www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - Bypassing std.concurrency.exec()

reply "Don Viszneki" <donny.viszneki gmail.com> writes:
I am using SDL2 for audio output. SDL2 creates its own thread 
which will periodically invoke my callback when the audio sink 
needs more samples.

I want to use std.concurrency.receiveTimeout() with this thread, 
however I get a segfault when attempting to receive a message:

http://pastebin.mozilla.org/5849384

Upon further investigation, it looks like this function depends 
on the TLS variable std.concurrency.mbox, which is marked 
private. (This is not strictly the same variable as 
std.concurrency.Tid.mbox.)

I think the problem can be found by examining the private 
function std.concurrency._spawn(), which is the only place where 
std.concurrency.mbox is assigned to, except for in 
std.concurrency.thisTid().

My thinking on this is probably wrong, however, as adding a call 
to thisTid() does not fix the problem.

If anyone has any ideas, I'd be happy to hear them.

I'm using a really old DMD but I have compared the 
std.concurrency module from my GDC 4.9.0 with the latest from 
Github Phobos and they look substantially the same with respect 
to my issue.

Any help would be greatly appreciated!
Aug 06 2014
parent reply "Don Viszneki" <donny.viszneki gmail.com> writes:
On Thursday, 7 August 2014 at 05:16:59 UTC, Don Viszneki wrote:
 My thinking on this is probably wrong, however, as adding a 
 call to thisTid() does not fix the problem.
Well, I've confirmed using gdb that std.concurrency.mbox is properly assigned a new MessageBox in both my main thread and in my audio thread before the crash occurs. So I am no closer to identifying the problem!
Aug 06 2014
parent reply "Don Viszneki" <donny.viszneki gmail.com> writes:
On Thursday, 7 August 2014 at 05:23:51 UTC, Don Viszneki wrote:
 So I am no closer to identifying the problem!
Kapps in #d freenode suggested the problem is in the allocator not having registered This worked! However, we now have problems when shutting down. It appears that during garbage collection, a call to core.thread.suspend() throws the following exception:
throw new ThreadException( "Unable to suspend thread" )
Which results in an infinitely recursive loop, where the allocator continuously tries to throw exceptions! I think perhaps I need to give D the opportunity to clean up SDL2's audio thread before shutting it down?
Aug 06 2014
parent reply "Don Viszneki" <donny.viszneki gmail.com> writes:
On Thursday, 7 August 2014 at 05:58:50 UTC, Don Viszneki wrote:
 I think perhaps I need to give D the opportunity to clean up 
 SDL2's audio thread before shutting it down?
I added a new message that is sent first to my audio thread from the main thread when shutting down, and then it is sent from the audio thread to the main thread as acknowledgement. In audio thread: (MessageShutdownAudio msg) { send(mainTid, MessageShutdownAudio()); thread_detachThis(); SDL_PauseAudio(1); } In main thread: send(audioTid, MessageShutdownAudio()); receive((MessageShutdownAudio bye) { /* do nothing */ }); SDL_CloseAudio();
Aug 06 2014
parent "Johannes Blume" <jblume jblume.com> writes:
Another thing you should keep in mind is that thread_attachThis() 
does not invoke any module TLS constructors, so you should also 
call rt_moduleTlsCtor() unless you are absolutely sure none of 
the modules you use have one. Call rt_moduleTlsCtor() before you 
detach the thread. Those functions are not part of the official 
API, so you might have to declare them with

extern(C)
{
     void rt_moduleTlsCtor();
     void rt_moduleTlsDtor();
}
Aug 07 2014