Skip to content

Instantly share code, notes, and snippets.

@PetarKirov
Created July 21, 2017 22:16
Show Gist options
  • Save PetarKirov/af3468862f54ad34598e3514526ba5d4 to your computer and use it in GitHub Desktop.
Save PetarKirov/af3468862f54ad34598e3514526ba5d4 to your computer and use it in GitHub Desktop.
import std.stdio, core.sync.mutex;
import std.traits : lvalueOf;
struct Resource(T)
{
struct Payload
{
Mutex mtx;
int refCount;
T value;
}
align(1):
int x;
shared(Payload)* data;
@disable this();
this(T value)
{
this.data = new shared Payload(new shared Mutex(), 0, value);
}
private this(shared(Payload)* fromShared)
{
this.data = fromShared;
}
Resource!T load() shared
{
import core.atomic : atomicLoad;
return Resource!T(atomicLoad(this.data));
}
void store(Resource!T p) shared
{
import core.atomic : atomicStore;
atomicStore(this.data, p.data);
}
alias UseDg = void delegate(ref T);
void use(UseDg useDg)
{
data.mtx.lock_nothrow();
auto unshared = cast(Payload*)data;
useDg(unshared.value);
data.mtx.unlock_nothrow();
}
}
shared Resource!int primary = void;
Resource!int[4096] other = void;
shared static this()
{
foreach (int i; 0 .. other.length)
{
import std.conv : emplace;
(cast(Resource!int*)&other[i]).emplace(i);
}
primary = Resource!int(other[0].data);
}
void main()
{
import std.parallelism, std.range, std.stdio;
pragma (msg, primary.data.offsetof);
foreach (i; 1.iota.parallel)
{
primary.load.use((ref x)
{
});
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment