#pragma once
#include <stdbool.h>
#include <stdint.h>
#if defined( _MSC_VER ) && !defined( __clang__ )
#include <intrin.h>
static inline uint32_t b2CTZ32( uint32_t block )
{
unsigned long index;
_BitScanForward( &index, block );
return index;
}
static inline uint32_t b2CLZ32( uint32_t value )
{
#if 1
unsigned long index;
if ( _BitScanReverse( &index, value ) )
{
return 31 - index;
}
else
{
return 32;
}
#else #endif
}
static inline uint32_t b2CTZ64( uint64_t block )
{
unsigned long index;
#ifdef _WIN64
_BitScanForward64( &index, block );
#else
if ( (uint32_t)block != 0 )
{
_BitScanForward( &index, (uint32_t)block );
}
else
{
_BitScanForward( &index, (uint32_t)( block >> 32 ) );
index += 32;
}
#endif
return index;
}
#else
static inline uint32_t b2CTZ32( uint32_t block )
{
return __builtin_ctz( block );
}
static inline uint32_t b2CLZ32( uint32_t value )
{
return __builtin_clz( value );
}
static inline uint32_t b2CTZ64( uint64_t block )
{
return __builtin_ctzll( block );
}
#endif
static inline bool b2IsPowerOf2( int x )
{
return ( x & ( x - 1 ) ) == 0;
}
static inline int b2BoundingPowerOf2( int x )
{
if ( x <= 1 )
{
return 1;
}
return 32 - (int)b2CLZ32( (uint32_t)x - 1 );
}
static inline int b2RoundUpPowerOf2( int x )
{
if ( x <= 1 )
{
return 1;
}
return 1 << ( 32 - (int)b2CLZ32( (uint32_t)x - 1 ) );
}