diff options
author | David Robillard <d@drobilla.net> | 2023-05-04 06:20:05 -0400 |
---|---|---|
committer | David Robillard <d@drobilla.net> | 2023-05-04 06:20:05 -0400 |
commit | 54570dc09a0de4c4773e9ca7a6fef80c3bcdfc2e (patch) | |
tree | 8ed44deadeb79bb496c31e3b4dcab61df48b3dfa /include | |
parent | 8afe1814483ec10f1f425a60d1fc80fe6e3cd8f1 (diff) | |
download | chilbert-54570dc09a0de4c4773e9ca7a6fef80c3bcdfc2e.tar.gz chilbert-54570dc09a0de4c4773e9ca7a6fef80c3bcdfc2e.tar.bz2 chilbert-54570dc09a0de4c4773e9ca7a6fef80c3bcdfc2e.zip |
Fix MSVC build
Diffstat (limited to 'include')
-rw-r--r-- | include/chilbert/detail/MultiBitVec.hpp | 2 | ||||
-rw-r--r-- | include/chilbert/detail/operations.hpp | 47 |
2 files changed, 45 insertions, 4 deletions
diff --git a/include/chilbert/detail/MultiBitVec.hpp b/include/chilbert/detail/MultiBitVec.hpp index 9053a04..bf1802c 100644 --- a/include/chilbert/detail/MultiBitVec.hpp +++ b/include/chilbert/detail/MultiBitVec.hpp @@ -165,7 +165,7 @@ public: size_t find_first() const { for (size_t i = 0; i < num_racks(); ++i) { - const int j = chilbert::detail::find_first(rack(i)); + const auto j = chilbert::detail::find_first(rack(i)); if (j) { return (i * bits_per_rack) + static_cast<size_t>(j); } diff --git a/include/chilbert/detail/operations.hpp b/include/chilbert/detail/operations.hpp index ba9971e..5dd59db 100644 --- a/include/chilbert/detail/operations.hpp +++ b/include/chilbert/detail/operations.hpp @@ -8,6 +8,11 @@ #include "chilbert/detail/traits.hpp" #include "chilbert/operators.hpp" +#ifdef _MSC_VER +# include <immintrin.h> +# include <intrin.h> +#endif + #include <cassert> #include <climits> #include <cstddef> @@ -86,25 +91,59 @@ set_bit(T& field, const size_t index, const bool value) field.set(index, value); } +#ifdef _MSC_VER + +inline uint32_t +pop_count(const uint32_t field) +{ + return __popcnt(field); +} + +inline uint64_t +pop_count(const uint64_t field) +{ + return __popcnt64(field); +} + +#else + /// Return 1 + the index of the least significant 1-bit of `field`, or zero template<typename T> inline int -pop_count(const T& field); +pop_count(const T field); template<> inline int -pop_count<unsigned long>(const unsigned long& field) +pop_count<unsigned long>(const unsigned long field) { return __builtin_popcountl(field); } template<> inline int -pop_count<unsigned long long>(const unsigned long long& field) +pop_count<unsigned long long>(const unsigned long long field) { return __builtin_popcountll(field); } +#endif + +#ifdef _MSC_VER + +inline uint32_t +find_first(const uint32_t field) +{ + return field ? 1U + _tzcnt_u32(field) : 0U; +} + +inline uint64_t +find_first(const uint64_t field) +{ + return field ? 1U + _tzcnt_u64(field) : 0U; +} + +#else + /// Return 1 + the index of the least significant 1-bit of `field`, or zero template<typename T> inline int @@ -124,6 +163,8 @@ find_first<unsigned long long>(const unsigned long long field) return __builtin_ffsll(static_cast<long long>(field)); } +#endif + /// Calculates the Gray Code of `value` in place template<typename T> std::enable_if_t<is_bitvec_v<T>> |