include/asm-i386/atomic.h
10185 #ifndef __ARCH_I386_ATOMIC__
10186 #define __ARCH_I386_ATOMIC__
10187
10188 /* Atomic operations that C can't guarantee us. Useful
10189 * for resource counting etc.. */
10190
10191 #ifdef __SMP__
10192 #define LOCK "lock ; "
10193 #else
10194 #define LOCK ""
10195 #endif
10196
10197 /* Make sure gcc doesn't try to be clever and move things
10198 * around on us. We need to use _exactly_ the address the
10199 * user gave us, not some alias that contains the same
10200 * information. */
10201 #define __atomic_fool_gcc(x) \
10202 (*(volatile struct { int a[100]; } *)x)
10203
10204 #ifdef __SMP__
10205 typedef struct { volatile int counter; } atomic_t;
10206 #else
10207 typedef struct { int counter; } atomic_t;
10208 #endif
10209
10210 #define ATOMIC_INIT(i) { (i) }
10211
10212 #define atomic_read(v) ((v)->counter)
10213 #define atomic_set(v,i) (((v)->counter) = (i))
10214
10215 static __inline__ void atomic_add(int i,
10216 volatile atomic_t *v)
10217 {
10218 __asm__ __volatile__(
10219 LOCK "addl %1,%0"
10220 :"=m" (__atomic_fool_gcc(v))
10221 :"ir" (i), "m" (__atomic_fool_gcc(v)));
10222 }
10223
10224 static __inline__ void atomic_sub(int i,
10225 volatile atomic_t *v)
10226 {
10227 __asm__ __volatile__(
10228 LOCK "subl %1,%0"
10229 :"=m" (__atomic_fool_gcc(v))
10230 :"ir" (i), "m" (__atomic_fool_gcc(v)));
10231 }
10232
10233 static __inline__ void atomic_inc(volatile atomic_t *v)
10234 {
10235 __asm__ __volatile__(
10236 LOCK "incl %0"
10237 :"=m" (__atomic_fool_gcc(v))
10238 :"m" (__atomic_fool_gcc(v)));
10239 }
10240
10241 static __inline__ void atomic_dec(volatile atomic_t *v)
10242 {
10243 __asm__ __volatile__(
10244 LOCK "decl %0"
10245 :"=m" (__atomic_fool_gcc(v))
10246 :"m" (__atomic_fool_gcc(v)));
10247 }
10248
10249 static __inline__ int atomic_dec_and_test(
10250 volatile atomic_t *v)
10251 {
10252 unsigned char c;
10253
10254 __asm__ __volatile__(
10255 LOCK "decl %0; sete %1"
10256 :"=m" (__atomic_fool_gcc(v)), "=qm" (c)
10257 :"m" (__atomic_fool_gcc(v)));
10258 return c != 0;
10259 }
10260
10261 /* These are x86-specific, used by some header files */
10262 #define atomic_clear_mask(mask, addr) \
10263 __asm__ __volatile__(LOCK "andl %0,%1" \
10264 : : "r" (~(mask)), \
10265 "m" (__atomic_fool_gcc(addr)) : "memory")
10266
10267 #define atomic_set_mask(mask, addr) \
10268 __asm__ __volatile__(LOCK "orl %0,%1" \
10269 : : "r" (mask),"m" (__atomic_fool_gcc(addr)) : "memory")
10270
10271 #endif
Сайт управляется системой
uCoz