root/include/asm-m68k/bitops.h

/* [previous][next][first][last][top][bottom][index][help] */

INCLUDED FROM


DEFINITIONS

This source file includes following definitions.
  1. set_bit
  2. clear_bit
  3. change_bit
  4. test_bit
  5. find_first_zero_bit
  6. find_next_zero_bit
  7. ffz
  8. find_first_one_bit
  9. find_next_one_bit
  10. minix_find_first_zero_bit
  11. minix_set_bit
  12. minix_clear_bit
  13. minix_test_bit
  14. ext2_set_bit
  15. ext2_clear_bit
  16. ext2_test_bit
  17. ext2_find_first_zero_bit
  18. ext2_find_next_zero_bit

   1 #ifndef _M68K_BITOPS_H
   2 #define _M68K_BITOPS_H
   3 /*
   4  * Copyright 1992, Linus Torvalds.
   5  *
   6  * This file is subject to the terms and conditions of the GNU General Public
   7  * License.  See the file README.legal in the main directory of this archive
   8  * for more details.
   9  */
  10 
  11 /*
  12  * Require 68020 or better.
  13  *
  14  * They use the standard big-endian m680x0 bit ordering.
  15  */
  16 
  17 extern __inline__ int set_bit(int nr,void * vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
  18 {
  19         char retval;
  20 
  21         __asm__ __volatile__ ("bfset %2@{%1:#1}; sne %0"
  22              : "=d" (retval) : "d" (nr^31), "a" (vaddr));
  23 
  24         return retval;
  25 }
  26 
  27 extern __inline__ int clear_bit(int nr, void * vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
  28 {
  29         char retval;
  30 
  31         __asm__ __volatile__ ("bfclr %2@{%1:#1}; sne %0"
  32              : "=d" (retval) : "d" (nr^31), "a" (vaddr));
  33 
  34         return retval;
  35 }
  36 
  37 extern __inline__ int change_bit(int nr, void * vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
  38 {
  39         char retval;
  40 
  41         __asm__ __volatile__ ("bfchg %2@{%1:#1}; sne %0"
  42              : "=d" (retval) : "d" (nr^31), "a" (vaddr));
  43 
  44         return retval;
  45 }
  46 
  47 extern __inline__ int test_bit(int nr, const void * vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
  48 {
  49         return ((1UL << (nr & 31)) & (((const unsigned int *) vaddr)[nr >> 5])) != 0;
  50 }
  51 
  52 extern __inline__ int find_first_zero_bit(void * vaddr, unsigned size)
     /* [previous][next][first][last][top][bottom][index][help] */
  53 {
  54         unsigned long *p = vaddr, *addr = vaddr;
  55         unsigned long allones = ~0UL;
  56         int res;
  57         unsigned long num;
  58 
  59         if (!size)
  60                 return 0;
  61 
  62         while (*p++ == allones)
  63         {
  64                 if (size <= 32)
  65                         return (p - addr) << 5;
  66                 size -= 32;
  67         }
  68 
  69         num = ~*--p;
  70         __asm__ __volatile__ ("bfffo %1{#0,#0},%0"
  71                               : "=d" (res) : "d" (num & -num));
  72         return ((p - addr) << 5) + (res ^ 31);
  73 }
  74 
  75 extern __inline__ int find_next_zero_bit (void *vaddr, int size,
     /* [previous][next][first][last][top][bottom][index][help] */
  76                                       int offset)
  77 {
  78         unsigned long *addr = vaddr;
  79         unsigned long *p = addr + (offset >> 5);
  80         int set = 0, bit = offset & 31UL, res;
  81 
  82         if (offset >= size)
  83                 return size;
  84 
  85         if (bit) {
  86                 unsigned long num = ~*p & (~0UL << bit);
  87 
  88                 /* Look for zero in first longword */
  89                 __asm__ __volatile__ ("bfffo %1{#0,#0},%0"
  90                                       : "=d" (res) : "d" (num & -num));
  91                 if (res < 32)
  92                         return (offset & ~31UL) + (res ^ 31);
  93                 set = 32 - bit;
  94                 p++;
  95         }
  96         /* No zero yet, search remaining full bytes for a zero */
  97         res = find_first_zero_bit (p, size - 32 * (p - addr));
  98         return (offset + set + res);
  99 }
 100 
 101 /*
 102  * ffz = Find First Zero in word. Undefined if no zero exists,
 103  * so code should check against ~0UL first..
 104  */
 105 extern __inline__ unsigned long ffz(unsigned long word)
     /* [previous][next][first][last][top][bottom][index][help] */
 106 {
 107         int res;
 108 
 109         __asm__ __volatile__ ("bfffo %1{#0,#0},%0"
 110                               : "=d" (res) : "d" (~word & -~word));
 111         return res ^ 31;
 112 }
 113 
 114 extern __inline__ int find_first_one_bit(void * vaddr, unsigned size)
     /* [previous][next][first][last][top][bottom][index][help] */
 115 {
 116         unsigned long *p = vaddr, *addr = vaddr;
 117         int res;
 118         unsigned long num;
 119 
 120         if (!size)
 121                 return 0;
 122 
 123         while (!*p++)
 124         {
 125                 if (size <= 32)
 126                         return (p - addr) << 5;
 127                 size -= 32;
 128         }
 129 
 130         num = *--p;
 131         __asm__ __volatile__ ("bfffo %1{#0,#0},%0"
 132                               : "=d" (res) : "d" (num & -num));
 133         return ((p - addr) << 5) + (res ^ 31);
 134 }
 135 
 136 extern __inline__ int find_next_one_bit (void *vaddr, int size,
     /* [previous][next][first][last][top][bottom][index][help] */
 137                                       int offset)
 138 {
 139         unsigned long *addr = vaddr;
 140         unsigned long *p = addr + (offset >> 5);
 141         int set = 0, bit = offset & 31UL, res;
 142 
 143         if (offset >= size)
 144                 return size;
 145 
 146         if (bit) {
 147                 unsigned long num = *p & (~0UL << bit);
 148 
 149                 /* Look for one in first longword */
 150                 __asm__ __volatile__ ("bfffo %1{#0,#0},%0"
 151                                       : "=d" (res) : "d" (num & -num));
 152                 if (res < 32)
 153                         return (offset & ~31UL) + (res ^ 31);
 154                 set = 32 - bit;
 155                 p++;
 156         }
 157         /* No one yet, search remaining full bytes for a one */
 158         res = find_first_one_bit (p, size - 32 * (p - addr));
 159         return (offset + set + res);
 160 }
 161 
 162 /* Bitmap functions for the minix filesystem */
 163 
 164 extern __inline__ int
 165 minix_find_first_zero_bit (const void *vaddr, unsigned size)
     /* [previous][next][first][last][top][bottom][index][help] */
 166 {
 167         const unsigned short *p = vaddr, *addr = vaddr;
 168         int res;
 169         unsigned short num;
 170 
 171         if (!size)
 172                 return 0;
 173 
 174         while (*p++ == 0xffff)
 175         {
 176                 if (size <= 16)
 177                         return (p - addr) << 4;
 178                 size -= 16;
 179         }
 180 
 181         num = ~*--p;
 182         __asm__ __volatile__ ("bfffo %1{#16,#16},%0"
 183                               : "=d" (res) : "d" (num & -num));
 184         return ((p - addr) << 4) + (res ^ 31);
 185 }
 186 
 187 extern __inline__ int
 188 minix_set_bit (int nr, void *vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 189 {
 190         char retval;
 191 
 192         __asm__ __volatile__ ("bfset %2{%1:#1}; sne %0"
 193              : "=d" (retval) : "d" (nr^15), "m" (*(char *)vaddr));
 194 
 195         return retval;
 196 }
 197 
 198 extern __inline__ int
 199 minix_clear_bit (int nr, void *vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 200 {
 201         char retval;
 202 
 203         __asm__ __volatile__ ("bfclr %2{%1:#1}; sne %0"
 204              : "=d" (retval) : "d" (nr^15), "m" (*(char *) vaddr));
 205 
 206         return retval;
 207 }
 208 
 209 extern __inline__ int
 210 minix_test_bit (int nr, const void *vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 211 {
 212         return ((1U << (nr & 15)) & (((const unsigned short *) vaddr)[nr >> 4])) != 0;
 213 }
 214 
 215 /* Bitmap functions for the ext2 filesystem. */
 216 
 217 extern __inline__ int
 218 ext2_set_bit (int nr, void *vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 219 {
 220         char retval;
 221 
 222         __asm__ __volatile__ ("bfset %2{%1,#1}; sne %0"
 223              : "=d" (retval) : "d" (nr^7), "m" (*(char *) vaddr));
 224 
 225         return retval;
 226 }
 227 
 228 extern __inline__ int
 229 ext2_clear_bit (int nr, void *vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 230 {
 231         char retval;
 232 
 233         __asm__ __volatile__ ("bfclr %2{%1,#1}; sne %0"
 234              : "=d" (retval) : "d" (nr^7), "m" (*(char *) vaddr));
 235 
 236         return retval;
 237 }
 238 
 239 extern __inline__ int
 240 ext2_test_bit (int nr, const void *vaddr)
     /* [previous][next][first][last][top][bottom][index][help] */
 241 {
 242         return ((1U << (nr & 7)) & (((const unsigned char *) vaddr)[nr >> 3])) != 0;
 243 }
 244 
 245 extern __inline__ int
 246 ext2_find_first_zero_bit (const void *vaddr, unsigned size)
     /* [previous][next][first][last][top][bottom][index][help] */
 247 {
 248         const unsigned long *p = vaddr, *addr = vaddr;
 249         int res;
 250 
 251         if (!size)
 252                 return 0;
 253 
 254         while (*p++ == ~0UL)
 255         {
 256                 if (size <= 32)
 257                         return (p - addr) << 5;
 258                 size -= 32;
 259         }
 260 
 261         --p;
 262         for (res = 0; res < 32; res++)
 263                 if (!ext2_test_bit (res, p))
 264                         break;
 265         return (p - addr) * 32 + res;
 266 }
 267 
 268 extern __inline__ int
 269 ext2_find_next_zero_bit (const void *vaddr, unsigned size, unsigned offset)
     /* [previous][next][first][last][top][bottom][index][help] */
 270 {
 271         const unsigned long *addr = vaddr;
 272         const unsigned long *p = addr + (offset >> 5);
 273         int bit = offset & 31UL, res;
 274 
 275         if (offset >= size)
 276                 return size;
 277 
 278         if (bit) {
 279                 /* Look for zero in first longword */
 280                 for (res = bit; res < 32; res++)
 281                         if (!ext2_test_bit (res, p))
 282                                 return (p - addr) * 32 + res;
 283                 p++;
 284         }
 285         /* No zero yet, search remaining full bytes for a zero */
 286         res = ext2_find_first_zero_bit (p, size - 32 * (p - addr));
 287         return (p - addr) * 32 + res;
 288 }
 289 
 290 #endif /* _M68K_BITOPS_H */

/* [previous][next][first][last][top][bottom][index][help] */