Annotation of Gnu-Mach/linux/src/include/asm-i386/bitops.h, revision 1.1.1.2

1.1       root        1: #ifndef _I386_BITOPS_H
                      2: #define _I386_BITOPS_H
                      3: 
                      4: /*
                      5:  * Copyright 1992, Linus Torvalds.
                      6:  */
                      7: 
                      8: /*
                      9:  * These have to be done with inline assembly: that way the bit-setting
                     10:  * is guaranteed to be atomic. All bit operations return 0 if the bit
                     11:  * was cleared before the operation and != 0 if it was not.
                     12:  *
                     13:  * bit 0 is the LSB of addr; bit 32 is the LSB of (addr+1).
                     14:  */
                     15: 
                     16: #ifdef __SMP__
                     17: #define LOCK_PREFIX "lock ; "
                     18: #define SMPVOL volatile
                     19: #else
                     20: #define LOCK_PREFIX ""
                     21: #define SMPVOL
                     22: #endif
                     23: 
                     24: /*
                     25:  * Some hacks to defeat gcc over-optimizations..
                     26:  */
                     27: struct __dummy { unsigned long a[100]; };
                     28: #define ADDR (*(struct __dummy *) addr)
                     29: #define CONST_ADDR (*(const struct __dummy *) addr)
                     30: 
                     31: extern __inline__ int set_bit(int nr, SMPVOL void * addr)
                     32: {
                     33:        int oldbit;
                     34: 
                     35:        __asm__ __volatile__(LOCK_PREFIX
                     36:                "btsl %2,%1\n\tsbbl %0,%0"
                     37:                :"=r" (oldbit),"=m" (ADDR)
                     38:                :"ir" (nr));
                     39:        return oldbit;
                     40: }
                     41: 
                     42: extern __inline__ int clear_bit(int nr, SMPVOL void * addr)
                     43: {
                     44:        int oldbit;
                     45: 
                     46:        __asm__ __volatile__(LOCK_PREFIX
                     47:                "btrl %2,%1\n\tsbbl %0,%0"
                     48:                :"=r" (oldbit),"=m" (ADDR)
                     49:                :"ir" (nr));
                     50:        return oldbit;
                     51: }
                     52: 
                     53: extern __inline__ int change_bit(int nr, SMPVOL void * addr)
                     54: {
                     55:        int oldbit;
                     56: 
                     57:        __asm__ __volatile__(LOCK_PREFIX
                     58:                "btcl %2,%1\n\tsbbl %0,%0"
                     59:                :"=r" (oldbit),"=m" (ADDR)
                     60:                :"ir" (nr));
                     61:        return oldbit;
                     62: }
                     63: 
1.1.1.2 ! root       64: extern __inline__ int test_and_set_bit(int nr, volatile void * addr)
        !            65: {
        !            66:        int oldbit;
        !            67: 
        !            68:        __asm__ __volatile__( LOCK_PREFIX
        !            69:                "btsl %2,%1\n\tsbbl %0,%0"
        !            70:                :"=r" (oldbit),"=m" (ADDR)
        !            71:                :"Ir" (nr));
        !            72:        return oldbit;
        !            73: }
        !            74: 
        !            75: extern __inline__ int test_and_clear_bit(int nr, volatile void * addr)
        !            76: {
        !            77:        int oldbit;
        !            78: 
        !            79:        __asm__ __volatile__( LOCK_PREFIX
        !            80:                "btrl %2,%1\n\tsbbl %0,%0"
        !            81:                :"=r" (oldbit),"=m" (ADDR)
        !            82:                :"Ir" (nr));
        !            83:        return oldbit;
        !            84: }
        !            85: 
        !            86: extern __inline__ int test_and_change_bit(int nr, volatile void * addr)
        !            87: {
        !            88:        int oldbit;
        !            89: 
        !            90:        __asm__ __volatile__( LOCK_PREFIX
        !            91:                "btcl %2,%1\n\tsbbl %0,%0"
        !            92:                :"=r" (oldbit),"=m" (ADDR)
        !            93:                :"Ir" (nr));
        !            94:        return oldbit;
        !            95: }
        !            96: 
        !            97: 
1.1       root       98: /*
                     99:  * This routine doesn't need to be atomic.
                    100:  */
                    101: extern __inline__ int test_bit(int nr, const SMPVOL void * addr)
                    102: {
                    103:        return ((1UL << (nr & 31)) & (((const unsigned int *) addr)[nr >> 5])) != 0;
                    104: }
                    105: 
                    106: /*
                    107:  * Find-bit routines..
                    108:  */
                    109: extern __inline__ int find_first_zero_bit(void * addr, unsigned size)
                    110: {
                    111:        int res;
                    112: 
                    113:        if (!size)
                    114:                return 0;
                    115:        __asm__("cld\n\t"
                    116:                "movl $-1,%%eax\n\t"
                    117:                "xorl %%edx,%%edx\n\t"
                    118:                "repe; scasl\n\t"
                    119:                "je 1f\n\t"
                    120:                "xorl -4(%%edi),%%eax\n\t"
                    121:                "subl $4,%%edi\n\t"
                    122:                "bsfl %%eax,%%edx\n"
                    123:                "1:\tsubl %%ebx,%%edi\n\t"
                    124:                "shll $3,%%edi\n\t"
                    125:                "addl %%edi,%%edx"
                    126:                :"=d" (res)
                    127:                :"c" ((size + 31) >> 5), "D" (addr), "b" (addr)
                    128:                :"ax", "cx", "di");
                    129:        return res;
                    130: }
                    131: 
                    132: extern __inline__ int find_next_zero_bit (void * addr, int size, int offset)
                    133: {
                    134:        unsigned long * p = ((unsigned long *) addr) + (offset >> 5);
                    135:        int set = 0, bit = offset & 31, res;
                    136:        
                    137:        if (bit) {
                    138:                /*
                    139:                 * Look for zero in first byte
                    140:                 */
                    141:                __asm__("bsfl %1,%0\n\t"
                    142:                        "jne 1f\n\t"
                    143:                        "movl $32, %0\n"
                    144:                        "1:"
                    145:                        : "=r" (set)
                    146:                        : "r" (~(*p >> bit)));
                    147:                if (set < (32 - bit))
                    148:                        return set + offset;
                    149:                set = 32 - bit;
                    150:                p++;
                    151:        }
                    152:        /*
                    153:         * No zero yet, search remaining full bytes for a zero
                    154:         */
                    155:        res = find_first_zero_bit (p, size - 32 * (p - (unsigned long *) addr));
                    156:        return (offset + set + res);
                    157: }
                    158: 
                    159: /*
                    160:  * ffz = Find First Zero in word. Undefined if no zero exists,
                    161:  * so code should check against ~0UL first..
                    162:  */
                    163: extern __inline__ unsigned long ffz(unsigned long word)
                    164: {
                    165:        __asm__("bsfl %1,%0"
                    166:                :"=r" (word)
                    167:                :"r" (~word));
                    168:        return word;
                    169: }
                    170: 
1.1.1.2 ! root      171: #ifdef __KERNEL__
        !           172: 
        !           173: /*
        !           174:  * ffs: find first bit set. This is defined the same way as
        !           175:  * the libc and compiler builtin ffs routines, therefore
        !           176:  * differs in spirit from the above ffz (man ffs).
        !           177:  */
        !           178: 
        !           179: extern __inline__ int ffs(int x)
        !           180: {
        !           181:        int r;
        !           182: 
        !           183:        __asm__("bsfl %1,%0\n\t"
        !           184:                "jnz 1f\n\t"
        !           185:                "movl $-1,%0\n"
        !           186:                "1:" : "=r" (r) : "g" (x));
        !           187:        return r+1;
        !           188: }
        !           189: 
        !           190: /*
        !           191:  * hweightN: returns the hamming weight (i.e. the number
        !           192:  * of bits set) of a N-bit word
        !           193:  */
        !           194: 
        !           195: #define hweight32(x) generic_hweight32(x)
        !           196: #define hweight16(x) generic_hweight16(x)
        !           197: #define hweight8(x) generic_hweight8(x)
        !           198: 
        !           199: #endif /* __KERNEL__ */
        !           200: 
1.1       root      201: #endif /* _I386_BITOPS_H */

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.