Skip to content

Commit

Permalink
adding a generic find_msb() implementation for types that support bit…
Browse files Browse the repository at this point in the history
… patterns
  • Loading branch information
Ravenwater committed Nov 13, 2024
1 parent f54385d commit 44eee26
Showing 1 changed file with 18 additions and 8 deletions.
26 changes: 18 additions & 8 deletions include/universal/utility/find_msb.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,22 @@ namespace sw { namespace universal {

//static const unsigned int bval[] = { 0,1,2,2,3,3,3,3,4,4,4,4,4,4,4,4 };

template<typename BitPatternType>
constexpr unsigned find_msb(const BitPatternType& x) {
constexpr unsigned nbits = x.nbits;
for (unsigned i = 0; i < nbits; ++i) {
unsigned bitIndex = nbits - 1 - i;
if (x.test(bitIndex)) return bitIndex + 1;
}
return 0;
}

/// <summary>
/// find most significant bit that is set
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(unsigned int x) {
inline constexpr unsigned find_msb(unsigned int x) {
// find the first non-zero bit
unsigned int base = 0;
if (x & 0xFFFF0000) { base += 16; x >>= 16; }
Expand All @@ -41,7 +51,7 @@ inline constexpr unsigned int find_msb(unsigned int x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(unsigned long x) {
inline constexpr unsigned find_msb(unsigned long x) {
// find the first non-zero bit
unsigned int base = 0;
if (x & 0xFFFF0000) { base += 16; x >>= 16; }
Expand All @@ -60,7 +70,7 @@ inline constexpr unsigned int find_msb(unsigned long x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(unsigned long long x) {
inline constexpr unsigned find_msb(unsigned long long x) {
// find the first non-zero bit
unsigned int base = 0;
if (x & 0xFFFFFFFF00000000) { base += 32; x >>= 32; }
Expand All @@ -82,7 +92,7 @@ inline constexpr unsigned int find_msb(unsigned long long x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(signed char x) {
inline constexpr unsigned find_msb(signed char x) {
// find the first non-zero bit
uint8_t tmp = uint8_t(x);
unsigned int base = 0;
Expand All @@ -100,7 +110,7 @@ inline constexpr unsigned int find_msb(signed char x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(short x) {
inline constexpr unsigned find_msb(short x) {
// find the first non-zero bit
uint16_t tmp = uint16_t(x);
unsigned int base = 0;
Expand All @@ -119,7 +129,7 @@ inline constexpr unsigned int find_msb(short x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(int x) {
inline constexpr unsigned find_msb(int x) {
// find the first non-zero bit
uint32_t tmp = uint32_t(x);
unsigned int base = 0;
Expand All @@ -139,7 +149,7 @@ inline constexpr unsigned int find_msb(int x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(long x) {
inline constexpr unsigned find_msb(long x) {
// find the first non-zero bit
uint32_t tmp = uint32_t(x);
unsigned int base = 0;
Expand All @@ -160,7 +170,7 @@ inline constexpr unsigned int find_msb(long x) {
/// </summary>
/// <param name="x">value to scan</param>
/// <returns> position of MSB that is set. LSB is defined to be at position 1, so no bits set returns 0</returns>
inline constexpr unsigned int find_msb(long long x) {
constexpr unsigned find_msb(long long x) {
// find the first non-zero bit
uint64_t tmp = uint64_t(x);
unsigned int base = 0;
Expand Down

0 comments on commit 44eee26

Please sign in to comment.