diff options
-rw-r--r-- | arch/h8300/Kconfig | 8 | ||||
-rw-r--r-- | include/asm-h8300/bitops.h | 222 |
2 files changed, 17 insertions, 213 deletions
diff --git a/arch/h8300/Kconfig b/arch/h8300/Kconfig index 98308b018a35..cabf0bfffc53 100644 --- a/arch/h8300/Kconfig +++ b/arch/h8300/Kconfig | |||
@@ -29,6 +29,14 @@ config RWSEM_XCHGADD_ALGORITHM | |||
29 | bool | 29 | bool |
30 | default n | 30 | default n |
31 | 31 | ||
32 | config GENERIC_FIND_NEXT_BIT | ||
33 | bool | ||
34 | default y | ||
35 | |||
36 | config GENERIC_HWEIGHT | ||
37 | bool | ||
38 | default y | ||
39 | |||
32 | config GENERIC_CALIBRATE_DELAY | 40 | config GENERIC_CALIBRATE_DELAY |
33 | bool | 41 | bool |
34 | default y | 42 | default y |
diff --git a/include/asm-h8300/bitops.h b/include/asm-h8300/bitops.h index af95f914e51c..574f57b6c4d1 100644 --- a/include/asm-h8300/bitops.h +++ b/include/asm-h8300/bitops.h | |||
@@ -8,7 +8,6 @@ | |||
8 | 8 | ||
9 | #include <linux/config.h> | 9 | #include <linux/config.h> |
10 | #include <linux/compiler.h> | 10 | #include <linux/compiler.h> |
11 | #include <asm/byteorder.h> /* swab32 */ | ||
12 | #include <asm/system.h> | 11 | #include <asm/system.h> |
13 | 12 | ||
14 | #ifdef __KERNEL__ | 13 | #ifdef __KERNEL__ |
@@ -177,10 +176,7 @@ H8300_GEN_TEST_BITOP(test_and_change_bit,"bnot") | |||
177 | #undef H8300_GEN_TEST_BITOP_CONST_INT | 176 | #undef H8300_GEN_TEST_BITOP_CONST_INT |
178 | #undef H8300_GEN_TEST_BITOP | 177 | #undef H8300_GEN_TEST_BITOP |
179 | 178 | ||
180 | #define find_first_zero_bit(addr, size) \ | 179 | #include <asm-generic/bitops/ffs.h> |
181 | find_next_zero_bit((addr), (size), 0) | ||
182 | |||
183 | #define ffs(x) generic_ffs(x) | ||
184 | 180 | ||
185 | static __inline__ unsigned long __ffs(unsigned long word) | 181 | static __inline__ unsigned long __ffs(unsigned long word) |
186 | { | 182 | { |
@@ -196,216 +192,16 @@ static __inline__ unsigned long __ffs(unsigned long word) | |||
196 | return result; | 192 | return result; |
197 | } | 193 | } |
198 | 194 | ||
199 | static __inline__ int find_next_zero_bit (const unsigned long * addr, int size, int offset) | 195 | #include <asm-generic/bitops/find.h> |
200 | { | 196 | #include <asm-generic/bitops/sched.h> |
201 | unsigned long *p = (unsigned long *)(((unsigned long)addr + (offset >> 3)) & ~3); | 197 | #include <asm-generic/bitops/hweight.h> |
202 | unsigned long result = offset & ~31UL; | 198 | #include <asm-generic/bitops/ext2-non-atomic.h> |
203 | unsigned long tmp; | 199 | #include <asm-generic/bitops/ext2-atomic.h> |
204 | 200 | #include <asm-generic/bitops/minix.h> | |
205 | if (offset >= size) | ||
206 | return size; | ||
207 | size -= result; | ||
208 | offset &= 31UL; | ||
209 | if (offset) { | ||
210 | tmp = *(p++); | ||
211 | tmp |= ~0UL >> (32-offset); | ||
212 | if (size < 32) | ||
213 | goto found_first; | ||
214 | if (~tmp) | ||
215 | goto found_middle; | ||
216 | size -= 32; | ||
217 | result += 32; | ||
218 | } | ||
219 | while (size & ~31UL) { | ||
220 | if (~(tmp = *(p++))) | ||
221 | goto found_middle; | ||
222 | result += 32; | ||
223 | size -= 32; | ||
224 | } | ||
225 | if (!size) | ||
226 | return result; | ||
227 | tmp = *p; | ||
228 | |||
229 | found_first: | ||
230 | tmp |= ~0UL << size; | ||
231 | found_middle: | ||
232 | return result + ffz(tmp); | ||
233 | } | ||
234 | |||
235 | static __inline__ unsigned long find_next_bit(const unsigned long *addr, | ||
236 | unsigned long size, unsigned long offset) | ||
237 | { | ||
238 | unsigned long *p = (unsigned long *)(((unsigned long)addr + (offset >> 3)) & ~3); | ||
239 | unsigned int result = offset & ~31UL; | ||
240 | unsigned int tmp; | ||
241 | |||
242 | if (offset >= size) | ||
243 | return size; | ||
244 | size -= result; | ||
245 | offset &= 31UL; | ||
246 | if (offset) { | ||
247 | tmp = *(p++); | ||
248 | tmp &= ~0UL << offset; | ||
249 | if (size < 32) | ||
250 | goto found_first; | ||
251 | if (tmp) | ||
252 | goto found_middle; | ||
253 | size -= 32; | ||
254 | result += 32; | ||
255 | } | ||
256 | while (size >= 32) { | ||
257 | if ((tmp = *p++) != 0) | ||
258 | goto found_middle; | ||
259 | result += 32; | ||
260 | size -= 32; | ||
261 | } | ||
262 | if (!size) | ||
263 | return result; | ||
264 | tmp = *p; | ||
265 | |||
266 | found_first: | ||
267 | tmp &= ~0UL >> (32 - size); | ||
268 | if (tmp == 0UL) | ||
269 | return result + size; | ||
270 | found_middle: | ||
271 | return result + __ffs(tmp); | ||
272 | } | ||
273 | |||
274 | #define find_first_bit(addr, size) find_next_bit(addr, size, 0) | ||
275 | |||
276 | /* | ||
277 | * Every architecture must define this function. It's the fastest | ||
278 | * way of searching a 140-bit bitmap where the first 100 bits are | ||
279 | * unlikely to be set. It's guaranteed that at least one of the 140 | ||
280 | * bits is cleared. | ||
281 | */ | ||
282 | static inline int sched_find_first_bit(unsigned long *b) | ||
283 | { | ||
284 | if (unlikely(b[0])) | ||
285 | return __ffs(b[0]); | ||
286 | if (unlikely(b[1])) | ||
287 | return __ffs(b[1]) + 32; | ||
288 | if (unlikely(b[2])) | ||
289 | return __ffs(b[2]) + 64; | ||
290 | if (b[3]) | ||
291 | return __ffs(b[3]) + 96; | ||
292 | return __ffs(b[4]) + 128; | ||
293 | } | ||
294 | |||
295 | /* | ||
296 | * hweightN: returns the hamming weight (i.e. the number | ||
297 | * of bits set) of a N-bit word | ||
298 | */ | ||
299 | |||
300 | #define hweight32(x) generic_hweight32(x) | ||
301 | #define hweight16(x) generic_hweight16(x) | ||
302 | #define hweight8(x) generic_hweight8(x) | ||
303 | |||
304 | static __inline__ int ext2_set_bit(int nr, volatile void * addr) | ||
305 | { | ||
306 | int mask, retval; | ||
307 | unsigned long flags; | ||
308 | volatile unsigned char *ADDR = (unsigned char *) addr; | ||
309 | |||
310 | ADDR += nr >> 3; | ||
311 | mask = 1 << (nr & 0x07); | ||
312 | local_irq_save(flags); | ||
313 | retval = (mask & *ADDR) != 0; | ||
314 | *ADDR |= mask; | ||
315 | local_irq_restore(flags); | ||
316 | return retval; | ||
317 | } | ||
318 | #define ext2_set_bit_atomic(lock, nr, addr) ext2_set_bit(nr, addr) | ||
319 | |||
320 | static __inline__ int ext2_clear_bit(int nr, volatile void * addr) | ||
321 | { | ||
322 | int mask, retval; | ||
323 | unsigned long flags; | ||
324 | volatile unsigned char *ADDR = (unsigned char *) addr; | ||
325 | |||
326 | ADDR += nr >> 3; | ||
327 | mask = 1 << (nr & 0x07); | ||
328 | local_irq_save(flags); | ||
329 | retval = (mask & *ADDR) != 0; | ||
330 | *ADDR &= ~mask; | ||
331 | local_irq_restore(flags); | ||
332 | return retval; | ||
333 | } | ||
334 | #define ext2_clear_bit_atomic(lock, nr, addr) ext2_set_bit(nr, addr) | ||
335 | |||
336 | static __inline__ int ext2_test_bit(int nr, const volatile void * addr) | ||
337 | { | ||
338 | int mask; | ||
339 | const volatile unsigned char *ADDR = (const unsigned char *) addr; | ||
340 | |||
341 | ADDR += nr >> 3; | ||
342 | mask = 1 << (nr & 0x07); | ||
343 | return ((mask & *ADDR) != 0); | ||
344 | } | ||
345 | |||
346 | #define ext2_find_first_zero_bit(addr, size) \ | ||
347 | ext2_find_next_zero_bit((addr), (size), 0) | ||
348 | |||
349 | static __inline__ unsigned long ext2_find_next_zero_bit(void *addr, unsigned long size, unsigned long offset) | ||
350 | { | ||
351 | unsigned long *p = ((unsigned long *) addr) + (offset >> 5); | ||
352 | unsigned long result = offset & ~31UL; | ||
353 | unsigned long tmp; | ||
354 | |||
355 | if (offset >= size) | ||
356 | return size; | ||
357 | size -= result; | ||
358 | offset &= 31UL; | ||
359 | if(offset) { | ||
360 | /* We hold the little endian value in tmp, but then the | ||
361 | * shift is illegal. So we could keep a big endian value | ||
362 | * in tmp, like this: | ||
363 | * | ||
364 | * tmp = __swab32(*(p++)); | ||
365 | * tmp |= ~0UL >> (32-offset); | ||
366 | * | ||
367 | * but this would decrease performance, so we change the | ||
368 | * shift: | ||
369 | */ | ||
370 | tmp = *(p++); | ||
371 | tmp |= __swab32(~0UL >> (32-offset)); | ||
372 | if(size < 32) | ||
373 | goto found_first; | ||
374 | if(~tmp) | ||
375 | goto found_middle; | ||
376 | size -= 32; | ||
377 | result += 32; | ||
378 | } | ||
379 | while(size & ~31UL) { | ||
380 | if(~(tmp = *(p++))) | ||
381 | goto found_middle; | ||
382 | result += 32; | ||
383 | size -= 32; | ||
384 | } | ||
385 | if(!size) | ||
386 | return result; | ||
387 | tmp = *p; | ||
388 | |||
389 | found_first: | ||
390 | /* tmp is little endian, so we would have to swab the shift, | ||
391 | * see above. But then we have to swab tmp below for ffz, so | ||
392 | * we might as well do this here. | ||
393 | */ | ||
394 | return result + ffz(__swab32(tmp) | (~0UL << size)); | ||
395 | found_middle: | ||
396 | return result + ffz(__swab32(tmp)); | ||
397 | } | ||
398 | |||
399 | /* Bitmap functions for the minix filesystem. */ | ||
400 | #define minix_test_and_set_bit(nr,addr) __test_and_set_bit(nr,addr) | ||
401 | #define minix_set_bit(nr,addr) __set_bit(nr,addr) | ||
402 | #define minix_test_and_clear_bit(nr,addr) __test_and_clear_bit(nr,addr) | ||
403 | #define minix_test_bit(nr,addr) test_bit(nr,addr) | ||
404 | #define minix_find_first_zero_bit(addr,size) find_first_zero_bit(addr,size) | ||
405 | 201 | ||
406 | #endif /* __KERNEL__ */ | 202 | #endif /* __KERNEL__ */ |
407 | 203 | ||
408 | #define fls(x) generic_fls(x) | 204 | #include <asm-generic/bitops/fls.h> |
409 | #define fls64(x) generic_fls64(x) | 205 | #include <asm-generic/bitops/fls64.h> |
410 | 206 | ||
411 | #endif /* _H8300_BITOPS_H */ | 207 | #endif /* _H8300_BITOPS_H */ |