Panda3D
pbitops.I
Go to the documentation of this file.
1 /**
2  * PANDA 3D SOFTWARE
3  * Copyright (c) Carnegie Mellon University. All rights reserved.
4  *
5  * All use of this software is subject to the terms of the revised BSD
6  * license. You should have received a copy of this license along
7  * with this source code in a file named "LICENSE."
8  *
9  * @file pbitops.I
10  * @author drose
11  * @date 2008-05-10
12  */
13 
14 /**
15  * Returns the number of 1 bits in the indicated word.
16  */
17 INLINE int
18 count_bits_in_word(uint16_t x) {
19  return (int)num_bits_on[x];
20 }
21 
22 /**
23  * Returns the number of 1 bits in the indicated word.
24  */
25 INLINE int
26 count_bits_in_word(uint32_t x) {
27 #if defined(__GNUC__) && defined(__POPCNT__)
28  return __builtin_popcount((unsigned int) x);
29 #else
30  return (int)num_bits_on[x & 0xffff] + (int)num_bits_on[(x >> 16) & 0xffff];
31 #endif
32 }
33 
34 /**
35  * Returns the number of 1 bits in the indicated word.
36  */
37 INLINE int
38 count_bits_in_word(uint64_t x) {
39 #if defined(__GNUC__) && defined(__POPCNT__)
40  return __builtin_popcountll((unsigned long long) x);
41 #else
42  return count_bits_in_word((uint32_t)x) + count_bits_in_word((uint32_t)(x >> 32));
43 #endif
44 }
45 
46 /**
47  * Returns a value such that every bit at or below the highest bit in x is 1.
48  */
49 INLINE uint16_t
50 flood_bits_down(uint16_t x) {
51  x |= (x >> 1);
52  x |= (x >> 2);
53  x |= (x >> 4);
54  x |= (x >> 8);
55  return x;
56 }
57 
58 /**
59  * Returns a value such that every bit at or below the highest bit in x is 1.
60  */
61 INLINE uint32_t
62 flood_bits_down(uint32_t x) {
63  x |= (x >> 1);
64  x |= (x >> 2);
65  x |= (x >> 4);
66  x |= (x >> 8);
67  x |= (x >> 16);
68  return x;
69 }
70 
71 /**
72  * Returns a value such that every bit at or below the highest bit in x is 1.
73  */
74 INLINE uint64_t
75 flood_bits_down(uint64_t x) {
76  x |= (x >> 1);
77  x |= (x >> 2);
78  x |= (x >> 4);
79  x |= (x >> 8);
80  x |= (x >> 16);
81  x |= (x >> 32);
82  return x;
83 }
84 
85 /**
86  * Returns a value such that every bit at or above the highest bit in x is 1.
87  */
88 INLINE uint16_t
89 flood_bits_up(uint16_t x) {
90  x |= (x << 1);
91  x |= (x << 2);
92  x |= (x << 4);
93  x |= (x << 8);
94  return x;
95 }
96 
97 /**
98  * Returns a value such that every bit at or above the highest bit in x is 1.
99  */
100 INLINE uint32_t
101 flood_bits_up(uint32_t x) {
102  x |= (x << 1);
103  x |= (x << 2);
104  x |= (x << 4);
105  x |= (x << 8);
106  x |= (x << 16);
107  return x;
108 }
109 
110 /**
111  * Returns a value such that every bit at or above the highest bit in x is 1.
112  */
113 INLINE uint64_t
114 flood_bits_up(uint64_t x) {
115  x |= (x << 1);
116  x |= (x << 2);
117  x |= (x << 4);
118  x |= (x << 8);
119  x |= (x << 16);
120  x |= (x << 32);
121  return x;
122 }
123 
124 /**
125  * Returns the index of the lowest 1 bit in the word. Returns -1 if there are
126  * no 1 bits.
127  */
128 INLINE int
129 get_lowest_on_bit(uint16_t x) {
130 #if defined(_MSC_VER)
131  unsigned long result;
132  return (_BitScanForward(&result, (unsigned long) x) == 0) ? -1 : result;
133 #elif defined(__GNUC__)
134  return __builtin_ffs((int) x) - 1;
135 #else
136  if (x == 0) {
137  return -1;
138  }
139 
140  uint16_t w = (x & (~x + 1));
141  return (int)num_bits_on[w - 1];
142 #endif
143 }
144 
145 /**
146  * Returns the index of the lowest 1 bit in the word. Returns -1 if there are
147  * no 1 bits.
148  */
149 INLINE int
150 get_lowest_on_bit(uint32_t x) {
151 #if defined(_MSC_VER)
152  unsigned long result;
153  return (_BitScanForward(&result, (unsigned long) x) == 0) ? -1 : result;
154 #elif defined(__GNUC__)
155  return __builtin_ffs((int) x) - 1;
156 #else
157  if (x == 0) {
158  return -1;
159  }
160 
161  uint32_t w = (x & (~x + 1));
162  return count_bits_in_word(w - 1);
163 #endif
164 }
165 
166 /**
167  * Returns the index of the lowest 1 bit in the word. Returns -1 if there are
168  * no 1 bits.
169  */
170 INLINE int
171 get_lowest_on_bit(uint64_t x) {
172 #if defined(_MSC_VER) && defined(_M_X64)
173  unsigned long result;
174  return (_BitScanForward64(&result, (unsigned __int64) x) == 0) ? -1 : result;
175 #elif defined(__GNUC__)
176  return __builtin_ffsll((long long) x) - 1;
177 #else
178  if (x == 0) {
179  return -1;
180  }
181 
182  uint64_t w = (x & (~x + 1));
183  return count_bits_in_word(w - 1);
184 #endif
185 }
186 
187 /**
188  * Returns the index of the highest 1 bit in the word. Returns -1 if there
189  * are no 1 bits.
190  */
191 INLINE int
192 get_highest_on_bit(uint16_t x) {
193 #if defined(_MSC_VER)
194  unsigned long result;
195  return (_BitScanReverse(&result, (unsigned long) x) == 0) ? -1 : result;
196 #elif defined(__GNUC__)
197  return (x == 0) ? -1 : 31 - __builtin_clz((unsigned int) x);
198 #else
199  uint16_t w = flood_bits_down(x);
200  return count_bits_in_word(w) - 1;
201 #endif
202 }
203 
204 /**
205  * Returns the index of the highest 1 bit in the word. Returns -1 if there
206  * are no 1 bits.
207  */
208 INLINE int
209 get_highest_on_bit(uint32_t x) {
210 #if defined(_MSC_VER)
211  unsigned long result;
212  return (_BitScanReverse(&result, (unsigned long) x) == 0) ? -1 : result;
213 #elif defined(__GNUC__)
214  return (x == 0) ? -1 : 31 - __builtin_clz((unsigned int) x);
215 #else
216  uint32_t w = flood_bits_down(x);
217  return count_bits_in_word(w) - 1;
218 #endif
219 }
220 
221 /**
222  * Returns the index of the highest 1 bit in the word. Returns -1 if there
223  * are no 1 bits.
224  */
225 INLINE int
226 get_highest_on_bit(uint64_t x) {
227 #if defined(_MSC_VER) && defined(_M_X64)
228  unsigned long result;
229  return (_BitScanReverse64(&result, (unsigned __int64) x) == 0) ? -1 : result;
230 #elif defined(__GNUC__)
231  return (x == 0) ? -1 : 63 - __builtin_clzll((unsigned long long) x);
232 #else
233  uint64_t w = flood_bits_down(x);
234  return count_bits_in_word(w) - 1;
235 #endif
236 }
237 
238 /**
239  * Returns the smallest power of 2 greater than x.
240  *
241  * Returns the smallest number n such that (1 << n) is larger than x.
242  */
243 INLINE int
244 get_next_higher_bit(uint16_t x) {
245  return get_highest_on_bit(x) + 1;
246 }
247 
248 /**
249  * Returns the smallest power of 2 greater than x.
250  *
251  * Returns the smallest number n such that (1 << n) is larger than x.
252  */
253 INLINE int
254 get_next_higher_bit(uint32_t x) {
255  return get_highest_on_bit(x) + 1;
256 }
257 
258 /**
259  * Returns the smallest power of 2 greater than x.
260  *
261  * Returns the smallest number n such that (1 << n) is larger than x.
262  */
263 INLINE int
264 get_next_higher_bit(uint64_t x) {
265  return get_highest_on_bit(x) + 1;
266 }
int get_next_higher_bit(uint16_t x)
Returns the smallest power of 2 greater than x.
Definition: pbitops.I:244
int count_bits_in_word(uint16_t x)
Returns the number of 1 bits in the indicated word.
Definition: pbitops.I:18
uint16_t flood_bits_down(uint16_t x)
Returns a value such that every bit at or below the highest bit in x is 1.
Definition: pbitops.I:50
int get_highest_on_bit(uint16_t x)
Returns the index of the highest 1 bit in the word.
Definition: pbitops.I:192
uint16_t flood_bits_up(uint16_t x)
Returns a value such that every bit at or above the highest bit in x is 1.
Definition: pbitops.I:89
int get_lowest_on_bit(uint16_t x)
Returns the index of the lowest 1 bit in the word.
Definition: pbitops.I:129