Wouldn't it be better to just redefine pthread_mutex_t to always be a shared 
type? Something like:

        struct pthread_mutex {...}
        alias shared(pthread_mutex) pthread_mutex_t;

or perhaps:

        shared struct phtread_mutex_t {...}


Le 2010-07-02 à 14:50, Andrei Alexandrescu a écrit :

> I think we should bite the bullet and mark the signatures as shared.
> 
> Andrei
> 
> Sean Kelly wrote:
>> As I'd feared, this is getting more and more complicated.  I tried making 
>> the lock() and unlock() methods in Mutex shared and now I'm getting these 
>> errors:
>> xtest.d(98): Error: function core.sys.posix.pthread.pthread_mutex_lock 
>> (pthread_mutex_t*) is not callable using argument types 
>> (shared(pthread_mutex_t)*)
>> xtest.d(98): Error: cannot implicitly convert expression (&this.m_hndl) of 
>> type shared(pthread_mutex_t)* to pthread_mutex_t*
>> xtest.d(120): Error: function core.sys.posix.pthread.pthread_mutex_unlock 
>> (pthread_mutex_t*) is not callable using argument types 
>> (shared(pthread_mutex_t)*)
>> xtest.d(120): Error: cannot implicitly convert expression (&this.m_hndl) of 
>> type shared(pthread_mutex_t)* to pthread_mutex_t*
>> xtest.d(146): Error: function core.sys.posix.pthread.pthread_mutex_trylock 
>> (pthread_mutex_t*) is not callable using argument types 
>> (shared(pthread_mutex_t)*)
>> xtest.d(146): Error: cannot implicitly convert expression (&this.m_hndl) of 
>> type shared(pthread_mutex_t)* to pthread_mutex_t*
>> While technically correct, I find this behavior quite frustrating.  I 
>> suppose I could go through the Posix API and mark all the thread stuff as 
>> shared to make sure it will compile correctly, but that would break any 
>> existing code that is using this stuff in an unshared data type (ie. 
>> basically everyone), and since these are extern (C) routines I can't 
>> overload them on shared either.  The simplest alternative fix I've found so 
>> far is basically what I described below:
>> class Mutex
>> {
>>    shared void lock()
>>    {
>>        (cast(Mutex) this).doLock();
>>    }
>>    private void doLock()
>>    {
>>        // lock the mutex
>>    }
>> }
>> I'm coming to wish there were a way to tell the compiler "this is part of 
>> the TCB, shut up, I know what I'm doing."
>> I think for the next release I'm simply going to allow sending Tid instances 
>> regardless of whether they contain an unshared reference so I can have more 
>> time to figure out the best way to handle this.
>> On Jun 30, 2010, at 1:37 PM, Sean Kelly wrote:
>>> Okay, alternate evil solution:
>>> 
>>> class Condition
>>> {
>>>   shared void notify()
>>>   {
>>>       static void doNotify() {}
>>>       (cast(Condition) this).doNotify();
>>>   }
>>> }
>>> 
>>> Seems like it should work, though I'm hoping that the classes in core.sync 
>>> are about the only ones where it's necessary (something similar will 
>>> probably be necessary for Mutex to make lock() and unlock() explicitly 
>>> callable, etc).  I'm half tempted to try labeling these functions as 
>>> __gshared and see if it compiles.
>>> 
>>> On Jun 30, 2010, at 1:24 PM, Sean Kelly wrote:
>>> 
>>>> Well that was a disaster.  I have this:
>>>> 
>>>> class MessageBox
>>>> {
>>>>  this()
>>>>  {
>>>>      // this makes m_lock the monitor for the MessageBox instance.
>>>>      m_lock = new Mutex( this );
>>>>      m_cond = new Condition( m_lock );
>>>>  }
>>>> 
>>>>  final synchronized void put( Message msg )
>>>>  {
>>>>      // m_lock is locked now
>>>>      m_list.add( msg );
>>>>      m_cond.notify(); // error: notify () is not callable using argument 
>>>> types () shared
>>>>  }
>>>> }
>>>> 
>>>> struct Tid
>>>> {
>>>>  shared MessageBox mbox;
>>>> }
>>>> 
>>>> class Condition
>>>> {
>>>>  void notify()
>>>>  {
>>>>      // fancy stuff involving semaphores
>>>>  }
>>>> }
>>>> 
>>>> How do I fix this?  Condition.notify() is technically shared, but I don't 
>>>> want to pay the cost for memory barriers that are utterly pointless.  
>>>> Should I change the call to notify() to:
>>>> 
>>>> (cast(Condition)m_cond).notify();
>>>> 
>>>> This should work, but it seems like an even worse subversion of the shared 
>>>> system than I'm already doing for MessageBox.  If it helps, MessageBox is 
>>>> a thread-local class instance with put() as its one shared public method, 
>>>> so other threads have a shared reference to MessageBox while the object's 
>>>> owner has a non-shared reference to it.  This is functionally correct, 
>>>> though it seems theoretically wrong to have both shared and unshared 
>>>> references to the same instance in the first place.
>> _______________________________________________
>> phobos mailing list
>> [email protected]
>> http://lists.puremagic.com/mailman/listinfo/phobos
> _______________________________________________
> phobos mailing list
> [email protected]
> http://lists.puremagic.com/mailman/listinfo/phobos

-- 
Michel Fortin
[email protected]
http://michelf.com/



_______________________________________________
phobos mailing list
[email protected]
http://lists.puremagic.com/mailman/listinfo/phobos

Reply via email to