diff --git a/examples/ToyPathTracer/Source/MathSimd.h b/examples/ToyPathTracer/Source/MathSimd.h index 3e0a5cbe..ef68ab9b 100644 --- a/examples/ToyPathTracer/Source/MathSimd.h +++ b/examples/ToyPathTracer/Source/MathSimd.h @@ -8,7 +8,7 @@ #define kSimdWidth 4 -#if !defined(__arm__) && !defined(__arm64__) && !defined(__EMSCRIPTEN__) +#if !defined(__arm__) && !defined(__arm64__) && !defined(__EMSCRIPTEN__) && !defined(_M_ARM64) // ---- SSE implementation @@ -141,8 +141,14 @@ VM_INLINE float hmin(float4 v) // Returns a 4-bit code where bit0..bit3 is X..W VM_INLINE unsigned mask(float4 v) { +#if defined(_M_ARM64) + static const uint32_t values[4] = { 1u, 2u, 4u, 8u }; + const uint32x4_t movemask = vld1q_u32( values ); + const uint32x4_t highbit = vdupq_n_u32( 0x80000000u ); +#else static const uint32x4_t movemask = { 1, 2, 4, 8 }; static const uint32x4_t highbit = { 0x80000000, 0x80000000, 0x80000000, 0x80000000 }; +#endif uint32x4_t t0 = vreinterpretq_u32_f32(v.m); uint32x4_t t1 = vtstq_u32(t0, highbit); uint32x4_t t2 = vandq_u32(t1, movemask); diff --git a/examples/ToyPathTracer/Source/Maths.h b/examples/ToyPathTracer/Source/Maths.h index b587715f..790aabd0 100644 --- a/examples/ToyPathTracer/Source/Maths.h +++ b/examples/ToyPathTracer/Source/Maths.h @@ -12,7 +12,7 @@ #if DO_FLOAT3_WITH_SIMD -#if !defined(__arm__) && !defined(__arm64__) +#if !defined(__arm__) && !defined(__arm64__) && !defined(_M_ARM64) // ---- SSE implementation @@ -223,8 +223,14 @@ VM_INLINE float3 cross(float3 a, float3 b) // Returns a 3-bit code where bit0..bit2 is X..Z VM_INLINE unsigned mask(float3 v) { +#if defined(_M_ARM64) + static const uint32_t values[4] = { 1u, 2u, 4u, 8u }; + const uint32x4_t movemask = vld1q_u32( values ); + const uint32x4_t highbit = vdupq_n_u32( 0x80000000u ); +#else static const uint32x4_t movemask = { 1, 2, 4, 8 }; static const uint32x4_t highbit = { 0x80000000, 0x80000000, 0x80000000, 0x80000000 }; +#endif uint32x4_t t0 = vreinterpretq_u32_f32(v.m); uint32x4_t t1 = vtstq_u32(t0, highbit); uint32x4_t t2 = vandq_u32(t1, movemask); diff --git a/examples/ToyPathTracer/Source/enkiTS/TaskScheduler.cpp b/examples/ToyPathTracer/Source/enkiTS/TaskScheduler.cpp index 187673ad..c3e86ed1 100644 --- a/examples/ToyPathTracer/Source/enkiTS/TaskScheduler.cpp +++ b/examples/ToyPathTracer/Source/enkiTS/TaskScheduler.cpp @@ -72,7 +72,11 @@ namespace #if defined _M_IX86 || defined _M_X64 #pragma intrinsic(_mm_pause) inline void Pause() { _mm_pause(); } - #endif + #elif defined(_M_ARM64) + inline void Pause() { __yield(); } + #else + inline void Pause() { /* No ops*/ } + #endif #elif defined __i386__ || defined __x86_64__ inline void Pause() { __asm__ __volatile__("pause;"); } #else diff --git a/profiler/src/winmain.cpp b/profiler/src/winmain.cpp index fd3c35f2..a2aa6958 100644 --- a/profiler/src/winmain.cpp +++ b/profiler/src/winmain.cpp @@ -14,6 +14,7 @@ int main( int argc, char** argv ); int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmd, int nCmd ) { +#if defined(_M_IX86) || defined(_M_X64) { uint32_t regs[4]; __cpuidex( (int*)regs, 0, 0 ); @@ -42,7 +43,7 @@ int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmd, return 0; } } - +#endif // x86/x64: AVX feature checks return main( __argc, __argv ); } #endif diff --git a/server/TracyPopcnt.hpp b/server/TracyPopcnt.hpp index 07b98fd8..38b828a1 100644 --- a/server/TracyPopcnt.hpp +++ b/server/TracyPopcnt.hpp @@ -13,6 +13,24 @@ static inline uint64_t TracyLzcnt( uint64_t i ) { return uint64_t( __builtin_clzll( i ) ); } +#elif defined(_M_ARM64) +#include +static inline uint64_t TracyCountBits( uint64_t i ) +{ + uint8x8_t v = vreinterpret_u8_u64( vdup_n_u64( i ) ); + uint8x8_t popcnt = vcnt_u8( v ); + return (uint64_t)vaddlv_u8( popcnt ); +} +static inline uint64_t TracyLzcnt( uint64_t i ) +{ + unsigned long index; + uint64_t leadingZeros = 64; + if( _BitScanReverse64( &index, i ) ) + { + leadingZeros = leadingZeros - 1 - index; + } + return leadingZeros; +} #elif defined _WIN64 # include # define TracyCountBits __popcnt64