xref: /netbsd-src/external/apache2/llvm/dist/libcxx/include/__bits (revision 4d6fc14bc9b0c5bf3e30be318c143ee82cadd108)
1*4d6fc14bSjoerg// -*- C++ -*-
2*4d6fc14bSjoerg//===----------------------------------------------------------------------===//
3*4d6fc14bSjoerg//
4*4d6fc14bSjoerg// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5*4d6fc14bSjoerg// See https://llvm.org/LICENSE.txt for license information.
6*4d6fc14bSjoerg// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7*4d6fc14bSjoerg//
8*4d6fc14bSjoerg//===----------------------------------------------------------------------===//
9*4d6fc14bSjoerg
10*4d6fc14bSjoerg#ifndef _LIBCPP___BITS
11*4d6fc14bSjoerg#define _LIBCPP___BITS
12*4d6fc14bSjoerg
13*4d6fc14bSjoerg#include <__config>
14*4d6fc14bSjoerg
15*4d6fc14bSjoerg#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
16*4d6fc14bSjoerg#pragma GCC system_header
17*4d6fc14bSjoerg#endif
18*4d6fc14bSjoerg
19*4d6fc14bSjoerg_LIBCPP_PUSH_MACROS
20*4d6fc14bSjoerg#include <__undef_macros>
21*4d6fc14bSjoerg
22*4d6fc14bSjoerg
23*4d6fc14bSjoerg_LIBCPP_BEGIN_NAMESPACE_STD
24*4d6fc14bSjoerg
25*4d6fc14bSjoerg#ifndef _LIBCPP_COMPILER_MSVC
26*4d6fc14bSjoerg
27*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
28*4d6fc14bSjoergint __libcpp_ctz(unsigned __x)           _NOEXCEPT { return __builtin_ctz(__x); }
29*4d6fc14bSjoerg
30*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
31*4d6fc14bSjoergint __libcpp_ctz(unsigned long __x)      _NOEXCEPT { return __builtin_ctzl(__x); }
32*4d6fc14bSjoerg
33*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
34*4d6fc14bSjoergint __libcpp_ctz(unsigned long long __x) _NOEXCEPT { return __builtin_ctzll(__x); }
35*4d6fc14bSjoerg
36*4d6fc14bSjoerg
37*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
38*4d6fc14bSjoergint __libcpp_clz(unsigned __x)           _NOEXCEPT { return __builtin_clz(__x); }
39*4d6fc14bSjoerg
40*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
41*4d6fc14bSjoergint __libcpp_clz(unsigned long __x)      _NOEXCEPT { return __builtin_clzl(__x); }
42*4d6fc14bSjoerg
43*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
44*4d6fc14bSjoergint __libcpp_clz(unsigned long long __x) _NOEXCEPT { return __builtin_clzll(__x); }
45*4d6fc14bSjoerg
46*4d6fc14bSjoerg
47*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
48*4d6fc14bSjoergint __libcpp_popcount(unsigned __x)           _NOEXCEPT { return __builtin_popcount(__x); }
49*4d6fc14bSjoerg
50*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
51*4d6fc14bSjoergint __libcpp_popcount(unsigned long __x)      _NOEXCEPT { return __builtin_popcountl(__x); }
52*4d6fc14bSjoerg
53*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
54*4d6fc14bSjoergint __libcpp_popcount(unsigned long long __x) _NOEXCEPT { return __builtin_popcountll(__x); }
55*4d6fc14bSjoerg
56*4d6fc14bSjoerg#else  // _LIBCPP_COMPILER_MSVC
57*4d6fc14bSjoerg
58*4d6fc14bSjoerg// Precondition:  __x != 0
59*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY
60*4d6fc14bSjoergint __libcpp_ctz(unsigned __x) {
61*4d6fc14bSjoerg  static_assert(sizeof(unsigned) == sizeof(unsigned long), "");
62*4d6fc14bSjoerg  static_assert(sizeof(unsigned long) == 4, "");
63*4d6fc14bSjoerg  unsigned long __where;
64*4d6fc14bSjoerg  if (_BitScanForward(&__where, __x))
65*4d6fc14bSjoerg    return static_cast<int>(__where);
66*4d6fc14bSjoerg  return 32;
67*4d6fc14bSjoerg}
68*4d6fc14bSjoerg
69*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY
70*4d6fc14bSjoergint __libcpp_ctz(unsigned long __x) {
71*4d6fc14bSjoerg    static_assert(sizeof(unsigned long) == sizeof(unsigned), "");
72*4d6fc14bSjoerg    return __ctz(static_cast<unsigned>(__x));
73*4d6fc14bSjoerg}
74*4d6fc14bSjoerg
75*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY
76*4d6fc14bSjoergint __libcpp_ctz(unsigned long long __x) {
77*4d6fc14bSjoerg    unsigned long __where;
78*4d6fc14bSjoerg#if defined(_LIBCPP_HAS_BITSCAN64)
79*4d6fc14bSjoerg  if (_BitScanForward64(&__where, __x))
80*4d6fc14bSjoerg    return static_cast<int>(__where);
81*4d6fc14bSjoerg#else
82*4d6fc14bSjoerg  // Win32 doesn't have _BitScanForward64 so emulate it with two 32 bit calls.
83*4d6fc14bSjoerg  if (_BitScanForward(&__where, static_cast<unsigned long>(__x)))
84*4d6fc14bSjoerg    return static_cast<int>(__where);
85*4d6fc14bSjoerg  if (_BitScanForward(&__where, static_cast<unsigned long>(__x >> 32)))
86*4d6fc14bSjoerg    return static_cast<int>(__where + 32);
87*4d6fc14bSjoerg#endif
88*4d6fc14bSjoerg  return 64;
89*4d6fc14bSjoerg}
90*4d6fc14bSjoerg
91*4d6fc14bSjoerg// Precondition:  __x != 0
92*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY
93*4d6fc14bSjoergint __libcpp_clz(unsigned __x) {
94*4d6fc14bSjoerg  static_assert(sizeof(unsigned) == sizeof(unsigned long), "");
95*4d6fc14bSjoerg  static_assert(sizeof(unsigned long) == 4, "");
96*4d6fc14bSjoerg  unsigned long __where;
97*4d6fc14bSjoerg  if (_BitScanReverse(&__where, __x))
98*4d6fc14bSjoerg    return static_cast<int>(31 - __where);
99*4d6fc14bSjoerg  return 32; // Undefined Behavior.
100*4d6fc14bSjoerg}
101*4d6fc14bSjoerg
102*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY
103*4d6fc14bSjoergint __libcpp_clz(unsigned long __x) {
104*4d6fc14bSjoerg    static_assert(sizeof(unsigned) == sizeof(unsigned long), "");
105*4d6fc14bSjoerg    return __libcpp_clz(static_cast<unsigned>(__x));
106*4d6fc14bSjoerg}
107*4d6fc14bSjoerg
108*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY
109*4d6fc14bSjoergint __libcpp_clz(unsigned long long __x) {
110*4d6fc14bSjoerg  unsigned long __where;
111*4d6fc14bSjoerg#if defined(_LIBCPP_HAS_BITSCAN64)
112*4d6fc14bSjoerg  if (_BitScanReverse64(&__where, __x))
113*4d6fc14bSjoerg    return static_cast<int>(63 - __where);
114*4d6fc14bSjoerg#else
115*4d6fc14bSjoerg  // Win32 doesn't have _BitScanReverse64 so emulate it with two 32 bit calls.
116*4d6fc14bSjoerg  if (_BitScanReverse(&__where, static_cast<unsigned long>(__x >> 32)))
117*4d6fc14bSjoerg    return static_cast<int>(63 - (__where + 32));
118*4d6fc14bSjoerg  if (_BitScanReverse(&__where, static_cast<unsigned long>(__x)))
119*4d6fc14bSjoerg    return static_cast<int>(63 - __where);
120*4d6fc14bSjoerg#endif
121*4d6fc14bSjoerg  return 64; // Undefined Behavior.
122*4d6fc14bSjoerg}
123*4d6fc14bSjoerg
124*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY int __libcpp_popcount(unsigned __x) {
125*4d6fc14bSjoerg  static_assert(sizeof(unsigned) == 4, "");
126*4d6fc14bSjoerg  return __popcnt(__x);
127*4d6fc14bSjoerg}
128*4d6fc14bSjoerg
129*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY int __libcpp_popcount(unsigned long __x) {
130*4d6fc14bSjoerg  static_assert(sizeof(unsigned long) == 4, "");
131*4d6fc14bSjoerg  return __popcnt(__x);
132*4d6fc14bSjoerg}
133*4d6fc14bSjoerg
134*4d6fc14bSjoerginline _LIBCPP_INLINE_VISIBILITY int __libcpp_popcount(unsigned long long __x) {
135*4d6fc14bSjoerg  static_assert(sizeof(unsigned long long) == 8, "");
136*4d6fc14bSjoerg  return __popcnt64(__x);
137*4d6fc14bSjoerg}
138*4d6fc14bSjoerg
139*4d6fc14bSjoerg#endif // _LIBCPP_COMPILER_MSVC
140*4d6fc14bSjoerg
141*4d6fc14bSjoerg_LIBCPP_END_NAMESPACE_STD
142*4d6fc14bSjoerg
143*4d6fc14bSjoerg_LIBCPP_POP_MACROS
144*4d6fc14bSjoerg
145*4d6fc14bSjoerg#endif // _LIBCPP___BITS
146