home *** CD-ROM | disk | FTP | other *** search
/ PC Welt 2006 November (DVD) / PCWELT_11_2006.ISO / casper / filesystem.squashfs / usr / src / linux-headers-2.6.17-6 / include / asm-frv / bitops.h < prev    next >
Encoding:
C/C++ Source or Header  |  2006-08-11  |  4.2 KB  |  190 lines

  1. /* bitops.h: bit operations for the Fujitsu FR-V CPUs
  2.  *
  3.  * For an explanation of how atomic ops work in this arch, see:
  4.  *   Documentation/fujitsu/frv/atomic-ops.txt
  5.  *
  6.  * Copyright (C) 2004 Red Hat, Inc. All Rights Reserved.
  7.  * Written by David Howells (dhowells@redhat.com)
  8.  *
  9.  * This program is free software; you can redistribute it and/or
  10.  * modify it under the terms of the GNU General Public License
  11.  * as published by the Free Software Foundation; either version
  12.  * 2 of the License, or (at your option) any later version.
  13.  */
  14. #ifndef _ASM_BITOPS_H
  15. #define _ASM_BITOPS_H
  16.  
  17. #include <linux/compiler.h>
  18. #include <asm/byteorder.h>
  19. #include <asm/system.h>
  20. #include <asm/atomic.h>
  21.  
  22. #ifdef __KERNEL__
  23.  
  24. #include <asm-generic/bitops/ffz.h>
  25.  
  26. /*
  27.  * clear_bit() doesn't provide any barrier for the compiler.
  28.  */
  29. #define smp_mb__before_clear_bit()    barrier()
  30. #define smp_mb__after_clear_bit()    barrier()
  31.  
  32. static inline int test_and_clear_bit(int nr, volatile void *addr)
  33. {
  34.     volatile unsigned long *ptr = addr;
  35.     unsigned long mask = 1UL << (nr & 31);
  36.     ptr += nr >> 5;
  37.     return (atomic_test_and_ANDNOT_mask(mask, ptr) & mask) != 0;
  38. }
  39.  
  40. static inline int test_and_set_bit(int nr, volatile void *addr)
  41. {
  42.     volatile unsigned long *ptr = addr;
  43.     unsigned long mask = 1UL << (nr & 31);
  44.     ptr += nr >> 5;
  45.     return (atomic_test_and_OR_mask(mask, ptr) & mask) != 0;
  46. }
  47.  
  48. static inline int test_and_change_bit(int nr, volatile void *addr)
  49. {
  50.     volatile unsigned long *ptr = addr;
  51.     unsigned long mask = 1UL << (nr & 31);
  52.     ptr += nr >> 5;
  53.     return (atomic_test_and_XOR_mask(mask, ptr) & mask) != 0;
  54. }
  55.  
  56. static inline void clear_bit(int nr, volatile void *addr)
  57. {
  58.     test_and_clear_bit(nr, addr);
  59. }
  60.  
  61. static inline void set_bit(int nr, volatile void *addr)
  62. {
  63.     test_and_set_bit(nr, addr);
  64. }
  65.  
  66. static inline void change_bit(int nr, volatile void * addr)
  67. {
  68.     test_and_change_bit(nr, addr);
  69. }
  70.  
  71. static inline void __clear_bit(int nr, volatile void * addr)
  72. {
  73.     volatile unsigned long *a = addr;
  74.     int mask;
  75.  
  76.     a += nr >> 5;
  77.     mask = 1 << (nr & 31);
  78.     *a &= ~mask;
  79. }
  80.  
  81. static inline void __set_bit(int nr, volatile void * addr)
  82. {
  83.     volatile unsigned long *a = addr;
  84.     int mask;
  85.  
  86.     a += nr >> 5;
  87.     mask = 1 << (nr & 31);
  88.     *a |= mask;
  89. }
  90.  
  91. static inline void __change_bit(int nr, volatile void *addr)
  92. {
  93.     volatile unsigned long *a = addr;
  94.     int mask;
  95.  
  96.     a += nr >> 5;
  97.     mask = 1 << (nr & 31);
  98.     *a ^= mask;
  99. }
  100.  
  101. static inline int __test_and_clear_bit(int nr, volatile void * addr)
  102. {
  103.     volatile unsigned long *a = addr;
  104.     int mask, retval;
  105.  
  106.     a += nr >> 5;
  107.     mask = 1 << (nr & 31);
  108.     retval = (mask & *a) != 0;
  109.     *a &= ~mask;
  110.     return retval;
  111. }
  112.  
  113. static inline int __test_and_set_bit(int nr, volatile void * addr)
  114. {
  115.     volatile unsigned long *a = addr;
  116.     int mask, retval;
  117.  
  118.     a += nr >> 5;
  119.     mask = 1 << (nr & 31);
  120.     retval = (mask & *a) != 0;
  121.     *a |= mask;
  122.     return retval;
  123. }
  124.  
  125. static inline int __test_and_change_bit(int nr, volatile void * addr)
  126. {
  127.     volatile unsigned long *a = addr;
  128.     int mask, retval;
  129.  
  130.     a += nr >> 5;
  131.     mask = 1 << (nr & 31);
  132.     retval = (mask & *a) != 0;
  133.     *a ^= mask;
  134.     return retval;
  135. }
  136.  
  137. /*
  138.  * This routine doesn't need to be atomic.
  139.  */
  140. static inline int __constant_test_bit(int nr, const volatile void * addr)
  141. {
  142.     return ((1UL << (nr & 31)) & (((const volatile unsigned int *) addr)[nr >> 5])) != 0;
  143. }
  144.  
  145. static inline int __test_bit(int nr, const volatile void * addr)
  146. {
  147.     int     * a = (int *) addr;
  148.     int    mask;
  149.  
  150.     a += nr >> 5;
  151.     mask = 1 << (nr & 0x1f);
  152.     return ((mask & *a) != 0);
  153. }
  154.  
  155. #define test_bit(nr,addr) \
  156. (__builtin_constant_p(nr) ? \
  157.  __constant_test_bit((nr),(addr)) : \
  158.  __test_bit((nr),(addr)))
  159.  
  160. #include <asm-generic/bitops/ffs.h>
  161. #include <asm-generic/bitops/__ffs.h>
  162. #include <asm-generic/bitops/find.h>
  163.  
  164. /*
  165.  * fls: find last bit set.
  166.  */
  167. #define fls(x)                        \
  168. ({                            \
  169.     int bit;                    \
  170.                             \
  171.     asm("scan %1,gr0,%0" : "=r"(bit) : "r"(x));    \
  172.                             \
  173.     bit ? 33 - bit : bit;                \
  174. })
  175.  
  176. #include <asm-generic/bitops/fls64.h>
  177. #include <asm-generic/bitops/sched.h>
  178. #include <asm-generic/bitops/hweight.h>
  179.  
  180. #include <asm-generic/bitops/ext2-non-atomic.h>
  181.  
  182. #define ext2_set_bit_atomic(lock,nr,addr)    test_and_set_bit  ((nr) ^ 0x18, (addr))
  183. #define ext2_clear_bit_atomic(lock,nr,addr)    test_and_clear_bit((nr) ^ 0x18, (addr))
  184.  
  185. #include <asm-generic/bitops/minix-le.h>
  186.  
  187. #endif /* __KERNEL__ */
  188.  
  189. #endif /* _ASM_BITOPS_H */
  190.