What sync object should i use?

Steven Schveighoffer schveiguy at yahoo.com
Tue May 14 11:26:51 PDT 2013


On Tue, 14 May 2013 13:59:51 -0400, Heinz <thor587 at gmail.com> wrote:

> Guys, this is a precise example of what i'm trying to do. You'll notice  
> that there're 2 ways of waking up the consumer:

2 things:

1. D mutex locks are re-entrant.  That is, you can do:

synchronized(mutex)
{
    synchronized(mutex)
    {
       ...
    }
}

and all is fine.

2. The condition logic in your code is wrong.  The condition/mutex  
protects the messages being sent to the consumer.

It seems that you have two messages (which is OK):

  - my_variable is present, needs to be processed
  - Run function 2 (flag loop == run function 2), set from inside the  
consumer, and some undisclosed threads.  I find this logic rather  
dangerous, but it is your app, I have no idea of the real meaning :)

So I would do it like this (names TBD based on your real use case)

void SetLoop(bool yesOrNo)
{
    synchronized(cond.mutex)
    {
        if((loop = yesOrNo) == true)
             cond.notify();
    }
}

void MyConsumer()
{
	while(true)
	{
                 Object _my_variable = null;
		synchronized(cond.mutex)
		{
			while(!loop && my_variable is null) // always wait for *real* messages  
to be set
				cond.wait();
			_my_variable = my_variable;
			my_variable = null; // consume
                 }

		// process local consumed copy of _my_variable *outside* of lock
		if(_my_variable !is null)
		{
			/*
			...
			Call private function 1. SetLoop(true/false) might be called here.
			...
			*/
		}
			
		// These conditions are intentionally placed here.
		synchronized(cond.mutex)
		{
			if(loop == false)
				continue; // Jump to next iteration. Please note that cond.mutex gets  
released and reaquired in the next iteration.
			else
				loop = false; // Reset waiting on every iteration. Can be modified by  
private function 2 below.
		}
			
		/*
		...
		Call private function 2. SetLoop(true/false) might be called here.
		...
		*/
	}
}

Then everything should be good.  I'd also add a "SetMyVariable" function  
too, akin to SetLoop.

-Steve


More information about the Digitalmars-d-learn mailing list