atomics.h 1.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061
  1. #pragma once
  2. #include "../../foundation/types.h"
  3. #include <Windows.h>
  4. #include <intrin.h>
  5. #ifdef __cplusplus
  6. #define NX_ATOMIC_INLINE inline
  7. #else
  8. #define NX_ATOMIC_INLINE
  9. #endif
  10. NX_ATOMIC_INLINE static size_t nx_atomic_inc(volatile size_t *addr)
  11. {
  12. return (size_t)_InterlockedIncrement((volatile LONG *)addr);
  13. }
  14. NX_ATOMIC_INLINE static size_t nx_atomic_dec(volatile size_t *addr)
  15. {
  16. return (size_t)_InterlockedDecrement((volatile LONG *)addr);
  17. }
  18. NX_ATOMIC_INLINE static size_t nx_atomic_dec_release(volatile size_t *addr)
  19. {
  20. return (size_t)_InterlockedDecrement((volatile LONG *)addr);
  21. }
  22. NX_ATOMIC_INLINE static void nx_atomic_write(size_t value, volatile size_t *addr)
  23. {
  24. InterlockedExchange((LONG *)addr, value);
  25. }
  26. NX_ATOMIC_INLINE static void nx_atomic_write_pointer(void *value, void* volatile *addr)
  27. {
  28. InterlockedExchangePointer(addr, value);
  29. }
  30. NX_ATOMIC_INLINE static size_t nx_atomic_add(size_t value, volatile size_t* addr)
  31. {
  32. return (size_t)InterlockedExchangeAdd((volatile LONG *)addr, (LONG)value);
  33. }
  34. NX_ATOMIC_INLINE static size_t nx_atomic_sub(size_t value, volatile size_t* addr)
  35. {
  36. return (size_t)InterlockedExchangeAdd((volatile LONG *)addr, -(LONG)value);
  37. }
  38. NX_ATOMIC_INLINE static void *nx_atomic_swap_pointer(const void *value, void* volatile *addr)
  39. {
  40. return InterlockedExchangePointer(addr, (PVOID)value);
  41. }
  42. NX_ATOMIC_INLINE static int nx_atomic_cmpxchg_pointer(void *oldvalue, void *newvalue, void* volatile *addr)
  43. {
  44. return InterlockedCompareExchangePointer(addr, newvalue, oldvalue) == oldvalue;
  45. }
  46. #pragma intrinsic(_InterlockedCompareExchange64)
  47. NX_ATOMIC_INLINE static int nx_atomic_cmpxchg2(int64_t oldvalue, int64_t newvalue, volatile int64_t *addr)
  48. {
  49. return _InterlockedCompareExchange64(addr, newvalue, oldvalue) == oldvalue;
  50. }