Bug 4957 – std.concurrency does not allow to pass Tid in struct fields
Status
RESOLVED
Resolution
FIXED
Severity
normal
Priority
P2
Component
phobos
Product
D
Version
D2
Platform
x86
OS
Linux
Creation time
2010-09-29T12:14:23Z
Last change time
2018-10-23T09:15:23Z
Keywords
pull
Assigned to
No Owner
Creator
osa8aso
Comments
Comment #0 by osa8aso — 2010-09-29T12:14:23Z
send() allows to Tid only as a top-level parameter. Using Tid in a struct does not work. This compiles:
----
import std.concurrency;
void main() {
send( thisTid, thisTid );
receive( Tid );
}
----
This fails to compile:
----
import std.concurrency;
struct Message { Tid tid; }
void main() {
send( thisTid, Message( thisTid ) );
receive( ( Message ) {} );
}
---
std/concurrency.d(363): Error: static assert "Aliases to mutable thread-local data not allowed."
c.d(4): instantiated from here: send!(Message)
So Tid is not mutable when passed to send() directly, but as a part of struct Message, it suddenly becomes mutable?
Comment #1 by ratchet.freak — 2011-05-12T15:28:20Z
I've found how it comes:
std.concurrency defines the following testing template for sending parameters along
//line 49
template hasLocalAliasing(T...)
{
static if( !T.length )
enum hasLocalAliasing = false;
else
enum hasLocalAliasing = (std.traits.hasLocalAliasing!(T[0]) && !is(T[0] == Tid)) ||
std.concurrency.hasLocalAliasing!(T[1 .. $]);
}
which handles Tid as a special case which doesn't happen when it's not top-level
Tid itself is of the form:
//lines 272
struct Tid
{
void send(T...)( T vals )
{
static assert( !hasLocalAliasing!(T),
"Aliases to mutable thread-local data not allowed." );
_send( this, vals );
}
private:
this( MessageBox m )
{
mbox = m;
}
MessageBox mbox;
}
MessageBox here does not pass the test of !std.traits.hasLocalAliasing (it's a class object)
quick fix: make mbox in Tid shared and cast accesses to it to thread local this allows Tid to pass the !std.traits.hasLocalAliasing test *as one would expect from it*
struct Tid
{
void send(T...)( T vals )
{
static assert( !hasLocalAliasing!(T),
"Aliases to mutable thread-local data not allowed." );
_send( this, vals );
}
private:
this( MessageBox m )
{
mbox = cast(shared)m;
}
shared MessageBox mbox;
}
//lines 419
private void _send(T...)( MsgType type, Tid tid, T vals )
{
(cast(MessageBox)tid.mbox).put( Message( type, vals ) );
}
Comment #2 by sean — 2011-05-16T11:23:18Z
Curses! Seems I'll have to apply 'shared' to private members of Tid.
Comment #3 by thepumpkin1979 — 2012-07-14T03:06:04Z
I ran into this issue too. We need a fix :(
Comment #4 by ratchet.freak — 2016-01-20T10:22:51Z