Concurrency Confusion

Chris via Digitalmars-d-learn digitalmars-d-learn at puremagic.com
Fri Aug 7 08:55:31 PDT 2015


On Thursday, 6 August 2015 at 21:17:15 UTC, 岩倉 澪 wrote:
> On Tuesday, 4 August 2015 at 08:35:10 UTC, Dicebot wrote:
>>     // in real app use `receiveTimeout` to do useful stuff 
>> until
>>     // result message is received
>>     auto output = receiveOnly!(immutable(Bar)[]);
>
> New question: how would I receive a immutable value with 
> receiveTimeout? I need the results from my worker thread 
> outside of the delegate that receiveTimeout takes.
>
> Also: what is the best way to kill off the worker thread when I 
> close the application, without having to wait for the worker 
> thread to complete? My first thought was to use receiveTimeout 
> in the worker thread, but the work is being done in a parallel 
> foreach loop, and I am not sure if there is a way to safely use 
> receiveTimeout in a parallel situation...
> I also found Thread.isDaemon in core.thread. I tried doing auto 
> thread = Thread.getThis(); thread.isDaemon = true; at the start 
> of the worker thread, but it still seems to wait for it to 
> complete before closing.
>
> Thanks again!

receiveTimeout can be used like this:

void main()
{
     spawn(&workerFunc);

     writeln("Waiting for a message");
     bool received = false;
     while (!received) {
         received = receiveTimeout(600.msecs,
                                   (string message) {  // <=== 
Receiving a value
                                       writeln("received: ", 
message);
                                 });

         if (!received) {
             writeln("... no message yet");

             /* ... other operations may be executed here ... */
         }
     }
}
(cf. http://ddili.org/ders/d.en/concurrency.html)

To stop threads immediately, I've found that the best way is to 
use a shared variable, typically a bool, that is changed only in 
one place. I hope I'll find the time on Monday to post a simple 
example.

1. shared bool ABORT;
2.
3.// in owner thread
4. ABORT = true;  // The only place where you do this.
5. bool res;
6. while ((res = receiveOnly!bool()) == false) { debug 
writeln("waiting for abort ..."); }



// in worker thread(s)

foreach ()
{
   if (ABORT)
     break;
   // working away
}
// ...
ownerTid.send(true);

If you have more than one thread to abort, you'll have to adapt 
lines 5 and 6 accordingly.

Unfortunately, sending an abort message to a thread as in 
`send(thread, true)` takes too long. Setting a global flag like 
ABORT is instantaneous. Beware of data races though. You might 
want to have a look at:

http://ddili.org/ders/d.en/concurrency_shared.html

Especially `synchronized` and atomicOp.


More information about the Digitalmars-d-learn mailing list