cpu.h 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. /*
  2. * Copyright 2010-2013 Branimir Karadzic. All rights reserved.
  3. * License: http://www.opensource.org/licenses/BSD-2-Clause
  4. */
  5. #ifndef BX_CPU_H_HEADER_GUARD
  6. #define BX_CPU_H_HEADER_GUARD
  7. #include "bx.h"
  8. #if BX_COMPILER_MSVC
  9. # if BX_PLATFORM_XBOX360
  10. # include <ppcintrinsics.h>
  11. # include <xtl.h>
  12. # else
  13. # include <math.h> // math.h is included because VS bitches:
  14. // warning C4985: 'ceil': attributes not present on previous declaration.
  15. // must be included before intrin.h.
  16. # include <intrin.h>
  17. # include <windows.h>
  18. # endif // !BX_PLATFORM_XBOX360
  19. extern "C" void _ReadBarrier();
  20. extern "C" void _WriteBarrier();
  21. extern "C" void _ReadWriteBarrier();
  22. # pragma intrinsic(_ReadBarrier)
  23. # pragma intrinsic(_WriteBarrier)
  24. # pragma intrinsic(_ReadWriteBarrier)
  25. # pragma intrinsic(_InterlockedIncrement)
  26. # pragma intrinsic(_InterlockedDecrement)
  27. #endif // BX_COMPILER_MSVC
  28. namespace bx
  29. {
  30. inline void readBarrier()
  31. {
  32. #if BX_COMPILER_MSVC
  33. _ReadBarrier();
  34. #elif BX_COMPILER_GCC || BX_COMPILER_CLANG
  35. asm volatile("":::"memory");
  36. #endif // BX_COMPILER
  37. }
  38. inline void writeBarrier()
  39. {
  40. #if BX_COMPILER_MSVC
  41. _WriteBarrier();
  42. #elif BX_COMPILER_GCC || BX_COMPILER_CLANG
  43. asm volatile("":::"memory");
  44. #endif // BX_COMPILER
  45. }
  46. inline void readWriteBarrier()
  47. {
  48. #if BX_COMPILER_MSVC
  49. _ReadWriteBarrier();
  50. #elif BX_COMPILER_GCC || BX_COMPILER_CLANG
  51. asm volatile("":::"memory");
  52. #endif // BX_COMPILER
  53. }
  54. inline void memoryBarrier()
  55. {
  56. #if BX_PLATFORM_XBOX360
  57. __lwsync();
  58. #elif BX_COMPILER_MSVC
  59. _mm_mfence();
  60. #else
  61. __sync_synchronize();
  62. // asm volatile("mfence":::"memory");
  63. #endif // BX_COMPILER
  64. }
  65. inline int32_t atomicIncr(volatile void* _var)
  66. {
  67. #if BX_COMPILER_MSVC
  68. return _InterlockedIncrement( (volatile LONG*)(_var) );
  69. #elif BX_COMPILER_GCC || BX_COMPILER_CLANG
  70. return __sync_fetch_and_add( (volatile int32_t*)_var, 1);
  71. #endif // BX_COMPILER
  72. }
  73. inline int32_t atomicDecr(volatile void* _var)
  74. {
  75. #if BX_COMPILER_MSVC
  76. return _InterlockedDecrement( (volatile LONG*)(_var) );
  77. #elif BX_COMPILER_GCC || BX_COMPILER_CLANG
  78. return __sync_fetch_and_sub( (volatile int32_t*)_var, 1);
  79. #endif // BX_COMPILER
  80. }
  81. inline void* atomicExchangePtr(void** _target, void* _ptr)
  82. {
  83. #if BX_COMPILER_MSVC
  84. return InterlockedExchangePointer(_target, _ptr);
  85. #elif BX_COMPILER_GCC || BX_COMPILER_CLANG
  86. return __sync_lock_test_and_set(_target, _ptr);
  87. #endif // BX_COMPILER
  88. }
  89. } // namespace bx
  90. #endif // BX_CPU_H_HEADER_GUARD