#pragma once namespace vm { template struct _to_atomic { static_assert(size == 4 || size == 8, "Invalid atomic type"); typedef T type; }; template struct _to_atomic { typedef uint32_t type; }; template struct _to_atomic { typedef uint64_t type; }; template class _atomic_base { volatile T data; typedef typename _to_atomic::type atomic_type; public: __forceinline const T compare_and_swap(const T cmp, const T exch) volatile { const atomic_type res = InterlockedCompareExchange((volatile atomic_type*)&data, (atomic_type&)exch, (atomic_type&)cmp); return (T&)res; } __forceinline const T exchange(const T value) volatile { const atomic_type res = InterlockedExchange((volatile atomic_type*)&data, (atomic_type&)value); return (T&)res; } __forceinline const T read_relaxed() const volatile { return (T&)data; } }; template struct atomic_le : public _atomic_base { }; template struct atomic_be : public _atomic_base::type> { }; namespace ps3 { template struct atomic : public atomic_be { }; } namespace psv { template struct atomic : public atomic_le { }; } using namespace ps3; }