1 /* atomic.c: atomic operations which got too long to be inlined all over
4 * Copyright 1999 Philipp Rumpf (prumpf@tux.org */
6 #include <linux/kernel.h>
7 #include <linux/spinlock.h>
8 #include <asm/system.h>
9 #include <asm/atomic.h>
12 spinlock_t __atomic_hash
[ATOMIC_HASH_SIZE
] = {
13 [0 ... (ATOMIC_HASH_SIZE
-1)] = SPIN_LOCK_UNLOCKED
17 spinlock_t __atomic_lock
= SPIN_LOCK_UNLOCKED
;
20 unsigned long __xchg(unsigned long x
, unsigned long *ptr
, int size
)
22 unsigned long temp
, flags
;
24 if (size
!= sizeof x
) {
25 printk("__xchg called with bad pointer\n");
27 spin_lock_irqsave(&__atomic_lock
, flags
);
30 spin_unlock_irqrestore(&__atomic_lock
, flags
);
34 unsigned long __xchg(unsigned long x
, unsigned long *ptr
, int size
)
36 unsigned long temp
, flags
;
41 spin_lock_irqsave(&__atomic_lock
, flags
);
44 spin_unlock_irqrestore(&__atomic_lock
, flags
);
48 ptr32
= (unsigned int *)ptr
;
49 spin_lock_irqsave(&__atomic_lock
, flags
);
50 temp
= (unsigned long)*ptr32
;
51 *ptr32
= (unsigned int)x
;
52 spin_unlock_irqrestore(&__atomic_lock
, flags
);
56 printk("__xchg called with bad pointer\n");