1 //===----------------------------------------------------------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 #ifndef _LIBCPP___RANDOM_LOG2_H
10 #define _LIBCPP___RANDOM_LOG2_H
12 #include <__cxx03/__config>
13 #include <__cxx03/__type_traits/conditional.h>
14 #include <__cxx03/cstddef>
16 #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
17 # pragma GCC system_header
20 _LIBCPP_BEGIN_NAMESPACE_STD
22 template <class _UIntType
, _UIntType _Xp
, size_t _Rp
>
25 template <unsigned long long _Xp
, size_t _Rp
>
26 struct __log2_imp
<unsigned long long, _Xp
, _Rp
> {
27 static const size_t value
=
28 _Xp
& ((unsigned long long)(1) << _Rp
) ? _Rp
: __log2_imp
<unsigned long long, _Xp
, _Rp
- 1>::value
;
31 template <unsigned long long _Xp
>
32 struct __log2_imp
<unsigned long long, _Xp
, 0> {
33 static const size_t value
= 0;
37 struct __log2_imp
<unsigned long long, 0, _Rp
> {
38 static const size_t value
= _Rp
+ 1;
41 #ifndef _LIBCPP_HAS_NO_INT128
43 template <__uint128_t _Xp
, size_t _Rp
>
44 struct __log2_imp
<__uint128_t
, _Xp
, _Rp
> {
45 static const size_t value
=
46 (_Xp
>> 64) ? (64 + __log2_imp
<unsigned long long, (_Xp
>> 64), 63>::value
)
47 : __log2_imp
<unsigned long long, _Xp
, 63>::value
;
50 #endif // _LIBCPP_HAS_NO_INT128
52 template <class _UIntType
, _UIntType _Xp
>
54 static const size_t value
= __log2_imp
<
55 #ifndef _LIBCPP_HAS_NO_INT128
56 __conditional_t
<sizeof(_UIntType
) <= sizeof(unsigned long long), unsigned long long, __uint128_t
>,
59 #endif // _LIBCPP_HAS_NO_INT128
61 sizeof(_UIntType
) * __CHAR_BIT__
- 1>::value
;
64 _LIBCPP_END_NAMESPACE_STD
66 #endif // _LIBCPP___RANDOM_LOG2_H