1 module libd.threading.atomic; 2 3 nothrow @nogc pure: 4 5 private extern(C) bool atomicCas8(ubyte* ifThis, ubyte equalsThis, ubyte setThis); 6 private extern(C) bool atomicCas16(ushort* ifThis, ushort equalsThis, ushort setThis); 7 private extern(C) bool atomicCas32(uint* ifThis, uint equalsThis, uint setThis); 8 private extern(C) bool atomicCas64(ulong* ifThis, ulong equalsThis, ulong setThis); 9 10 private extern(C) void atomicStore8(ubyte* dest, ubyte source); 11 private extern(C) void atomicStore16(ushort* dest, ushort source); 12 private extern(C) void atomicStore32(uint* dest, uint source); 13 private extern(C) void atomicStore64(ulong* dest, ulong source); 14 15 private extern(C) ubyte atomicLoad8(ubyte* value); 16 private extern(C) ushort atomicLoad16(ushort* value); 17 private extern(C) uint atomicLoad32(uint* value); 18 private extern(C) ulong atomicLoad64(ulong* value); 19 20 @trusted 21 bool atomicCas(T)(shared ref T ifThis, T equalsThis, T setItToThis) 22 { 23 static if(T.sizeof == 1) 24 return atomicCas8(cast(ubyte*)&ifThis, cast(ubyte)equalsThis, cast(ubyte)setItToThis); 25 else static if(T.sizeof == 2) 26 return atomicCas16(cast(ushort*)&ifThis, cast(ushort)equalsThis, cast(ushort)setItToThis); 27 else static if(T.sizeof == 4) 28 return atomicCas32(cast(uint*)&ifThis, cast(uint)equalsThis, cast(uint)setItToThis); 29 else static if(T.sizeof == 8) 30 return atomicCas16(cast(ulong*)&ifThis, cast(ulong)equalsThis, cast(ulong)setItToThis); 31 else 32 static assert(false, "Cannot use "~T.stringof~" with CAS."); 33 } 34 35 @trusted 36 void atomicStore(T)(shared ref T intoThis, T storeThis) 37 { 38 static if(T.sizeof == 1) 39 return atomicStore8(cast(ubyte*)&intoThis, cast(ubyte)storeThis); 40 else static if(T.sizeof == 2) 41 return atomicStore16(cast(ushort*)&intoThis, cast(ushort)storeThis); 42 else static if(T.sizeof == 4) 43 return atomicStore32(cast(uint*)&intoThis, cast(uint)storeThis); 44 else static if(T.sizeof == 8) 45 return atomicStore16(cast(ulong*)&intoThis, cast(ulong)storeThis); 46 else 47 static assert(false, "Cannot use "~T.stringof~" with XCHG."); 48 } 49 50 @trusted 51 T atomicLoad(T)(shared ref T value) 52 { 53 static if(T.sizeof == 1) 54 return cast(T)atomicLoad8(cast(ubyte*)&value); 55 else static if(T.sizeof == 2) 56 return cast(T)atomicLoad16(cast(ushort*)&value); 57 else static if(T.sizeof == 4) 58 return cast(T)atomicLoad32(cast(uint*)&value); 59 else static if(T.sizeof == 8) 60 return cast(T)atomicLoad16(cast(ulong*)&value); 61 else 62 static assert(false, "Cannot use "~T.stringof~" with XCHG."); 63 }