diff --git a/Inc/MockedDrivers/compiler_specific.hpp b/Inc/MockedDrivers/compiler_specific.hpp index 1524c886a..3e62d63c7 100644 --- a/Inc/MockedDrivers/compiler_specific.hpp +++ b/Inc/MockedDrivers/compiler_specific.hpp @@ -1,6 +1,12 @@ #pragma once #include +#if defined(_MSC_VER) +#define WIN32_LEAN_AND_MEAN +#include /* _BitScanForward, _BitScanReverse */ +#include /* _byteswap_ulong */ +#endif + /* * This file contains implementations or alternate names for * ARM GCC intrinsics that don't work on x86_64 / host platforms. @@ -38,7 +44,37 @@ static inline uint32_t __RBIT(uint32_t val) { return val; } -#define __CLZ __builtin_clz +inline uint32_t __CLZ(uint32_t val) { +#if defined(__GNUC__) || defined(__GNUG__) || defined(__clang__) + return __builtin_clz(val); +#elif defined(_MSC_VER) + DWORD idx = 0; + _BitScanReverse(&idx, val); + return 31 - idx; +#else + for (uint32_t i = 0; i < 32; i++) { + if ((val & (1 << (31 - i))) != 0) + return i; + } + return 32; +#endif +} + +inline uint32_t __CTZ(uint32_t val) { +#if defined(__GNUC__) || defined(__GNUG__) || defined(__clang__) + return __builtin_ctz(val); +#elif defined(_MSC_VER) + DWORD idx = 0; + _BitScanForward(&idx, val); + return idx; +#else + for (uint32_t i = 0; i < 32; i++) { + if ((val & (1 << i)) != 0) + return i; + } + return 32; +#endif +} #if defined(_MSC_VER) && (_MSC_VER > 1200) && !defined(__clang__) void _ReadWriteBarrier(void);