linux 2.6.16.38 w/ vs2.0.3-rc1
[linux-2.6.git] / include / asm-x86_64 / bitops.h
index 5dd7727..eb4df23 100644 (file)
@@ -29,7 +29,7 @@ static __inline__ void set_bit(int nr, volatile void * addr)
 {
        __asm__ __volatile__( LOCK_PREFIX
                "btsl %1,%0"
-               :"=m" (ADDR)
+               :"+m" (ADDR)
                :"dIr" (nr) : "memory");
 }
 
@@ -46,7 +46,7 @@ static __inline__ void __set_bit(int nr, volatile void * addr)
 {
        __asm__ volatile(
                "btsl %1,%0"
-               :"=m" (ADDR)
+               :"+m" (ADDR)
                :"dIr" (nr) : "memory");
 }
 
@@ -64,7 +64,7 @@ static __inline__ void clear_bit(int nr, volatile void * addr)
 {
        __asm__ __volatile__( LOCK_PREFIX
                "btrl %1,%0"
-               :"=m" (ADDR)
+               :"+m" (ADDR)
                :"dIr" (nr));
 }
 
@@ -72,7 +72,7 @@ static __inline__ void __clear_bit(int nr, volatile void * addr)
 {
        __asm__ __volatile__(
                "btrl %1,%0"
-               :"=m" (ADDR)
+               :"+m" (ADDR)
                :"dIr" (nr));
 }
 
@@ -92,7 +92,7 @@ static __inline__ void __change_bit(int nr, volatile void * addr)
 {
        __asm__ __volatile__(
                "btcl %1,%0"
-               :"=m" (ADDR)
+               :"+m" (ADDR)
                :"dIr" (nr));
 }
 
@@ -109,7 +109,7 @@ static __inline__ void change_bit(int nr, volatile void * addr)
 {
        __asm__ __volatile__( LOCK_PREFIX
                "btcl %1,%0"
-               :"=m" (ADDR)
+               :"+m" (ADDR)
                :"dIr" (nr));
 }
 
@@ -127,7 +127,7 @@ static __inline__ int test_and_set_bit(int nr, volatile void * addr)
 
        __asm__ __volatile__( LOCK_PREFIX
                "btsl %2,%1\n\tsbbl %0,%0"
-               :"=r" (oldbit),"=m" (ADDR)
+               :"=r" (oldbit),"+m" (ADDR)
                :"dIr" (nr) : "memory");
        return oldbit;
 }
@@ -147,7 +147,7 @@ static __inline__ int __test_and_set_bit(int nr, volatile void * addr)
 
        __asm__(
                "btsl %2,%1\n\tsbbl %0,%0"
-               :"=r" (oldbit),"=m" (ADDR)
+               :"=r" (oldbit),"+m" (ADDR)
                :"dIr" (nr));
        return oldbit;
 }
@@ -166,7 +166,7 @@ static __inline__ int test_and_clear_bit(int nr, volatile void * addr)
 
        __asm__ __volatile__( LOCK_PREFIX
                "btrl %2,%1\n\tsbbl %0,%0"
-               :"=r" (oldbit),"=m" (ADDR)
+               :"=r" (oldbit),"+m" (ADDR)
                :"dIr" (nr) : "memory");
        return oldbit;
 }
@@ -186,7 +186,7 @@ static __inline__ int __test_and_clear_bit(int nr, volatile void * addr)
 
        __asm__(
                "btrl %2,%1\n\tsbbl %0,%0"
-               :"=r" (oldbit),"=m" (ADDR)
+               :"=r" (oldbit),"+m" (ADDR)
                :"dIr" (nr));
        return oldbit;
 }
@@ -198,7 +198,7 @@ static __inline__ int __test_and_change_bit(int nr, volatile void * addr)
 
        __asm__ __volatile__(
                "btcl %2,%1\n\tsbbl %0,%0"
-               :"=r" (oldbit),"=m" (ADDR)
+               :"=r" (oldbit),"+m" (ADDR)
                :"dIr" (nr) : "memory");
        return oldbit;
 }
@@ -217,7 +217,7 @@ static __inline__ int test_and_change_bit(int nr, volatile void * addr)
 
        __asm__ __volatile__( LOCK_PREFIX
                "btcl %2,%1\n\tsbbl %0,%0"
-               :"=r" (oldbit),"=m" (ADDR)
+               :"=r" (oldbit),"+m" (ADDR)
                :"dIr" (nr) : "memory");
        return oldbit;
 }
@@ -340,6 +340,20 @@ static __inline__ unsigned long __ffs(unsigned long word)
        return word;
 }
 
+/*
+ * __fls: find last bit set.
+ * @word: The word to search
+ *
+ * Undefined if no zero exists, so code should check against ~0UL first.
+ */
+static __inline__ unsigned long __fls(unsigned long word)
+{
+       __asm__("bsrq %1,%0"
+               :"=r" (word)
+               :"rm" (word));
+       return word;
+}
+
 #ifdef __KERNEL__
 
 static inline int sched_find_first_bit(const unsigned long *b)
@@ -348,8 +362,7 @@ static inline int sched_find_first_bit(const unsigned long *b)
                return __ffs(b[0]);
        if (b[1])
                return __ffs(b[1]) + 64;
-       if (b[2])
-               return __ffs(b[2]) + 128;
+       return __ffs(b[2]) + 128;
 }
 
 /**
@@ -370,6 +383,35 @@ static __inline__ int ffs(int x)
        return r+1;
 }
 
+/**
+ * fls64 - find last bit set in 64 bit word
+ * @x: the word to search
+ *
+ * This is defined the same way as fls.
+ */
+static __inline__ int fls64(__u64 x)
+{
+       if (x == 0)
+               return 0;
+       return __fls(x) + 1;
+}
+
+/**
+ * fls - find last bit set
+ * @x: the word to search
+ *
+ * This is defined the same way as ffs.
+ */
+static __inline__ int fls(int x)
+{
+       int r;
+
+       __asm__("bsrl %1,%0\n\t"
+               "cmovzl %2,%0"
+               : "=&r" (r) : "rm" (x), "rm" (-1));
+       return r+1;
+}
+
 /**
  * hweightN - returns the hamming weight of a N-bit word
  * @x: the word to weigh
@@ -408,11 +450,6 @@ static __inline__ int ffs(int x)
 #define minix_find_first_zero_bit(addr,size) \
        find_first_zero_bit((void*)addr,size)
 
-/* find last set bit */
-#define fls(x) generic_fls(x)
-
-#define ARCH_HAS_ATOMIC_UNSIGNED 1
-
 #endif /* __KERNEL__ */
 
 #endif /* _X86_64_BITOPS_H */