Commit b77e5d86 authored by Anton Blanchard's avatar Anton Blanchard

Merge bk://ppc.bkbits.net/for-linus-ppc64

into samba.org:/scratch/anton/linux-2.5_ppc64
parents 88d02e13 40420e9b
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
#include <linux/unistd.h> #include <linux/unistd.h>
#include <linux/ptrace.h> #include <linux/ptrace.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/interrupt.h>
#include <asm/pgtable.h> #include <asm/pgtable.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
......
...@@ -245,8 +245,4 @@ EXPORT_SYMBOL(debugger_dabr_match); ...@@ -245,8 +245,4 @@ EXPORT_SYMBOL(debugger_dabr_match);
EXPORT_SYMBOL(debugger_fault_handler); EXPORT_SYMBOL(debugger_fault_handler);
#endif #endif
#ifdef CONFIG_SMP
EXPORT_SYMBOL(atomic_dec_and_lock);
#endif
EXPORT_SYMBOL(tb_ticks_per_usec); EXPORT_SYMBOL(tb_ticks_per_usec);
...@@ -60,6 +60,7 @@ ...@@ -60,6 +60,7 @@
#include <asm/time.h> #include <asm/time.h>
#include <asm/ppcdebug.h> #include <asm/ppcdebug.h>
#include <asm/prom.h>
void smp_local_timer_interrupt(struct pt_regs *); void smp_local_timer_interrupt(struct pt_regs *);
......
...@@ -4,6 +4,8 @@ ...@@ -4,6 +4,8 @@
O_TARGET = lib.o O_TARGET = lib.o
export-objs := dec_and_lock.o
obj-y := checksum.o dec_and_lock.o string.o strcase.o copypage.o \ obj-y := checksum.o dec_and_lock.o string.o strcase.o copypage.o \
memcpy.o copyuser.o memcpy.o copyuser.o
......
...@@ -7,32 +7,49 @@ ...@@ -7,32 +7,49 @@
* 2 of the License, or (at your option) any later version. * 2 of the License, or (at your option) any later version.
*/ */
#include <linux/module.h>
#include <linux/spinlock.h> #include <linux/spinlock.h>
#include <asm/system.h>
#include <asm/atomic.h> #include <asm/atomic.h>
#include <asm/system.h>
/*
* This is an implementation of the notion of "decrement a
* reference count, and return locked if it decremented to zero".
*
* This implementation can be used on any architecture that
* has a cmpxchg, and where atomic->value is an int holding
* the value of the atomic (i.e. the high bits aren't used
* for a lock or anything like that).
*
* N.B. ATOMIC_DEC_AND_LOCK gets defined in include/linux/spinlock.h
* if spinlocks are empty and thus atomic_dec_and_lock is defined
* to be atomic_dec_and_test - in that case we don't need it
* defined here as well.
*/
#ifndef ATOMIC_DEC_AND_LOCK
int atomic_dec_and_lock(atomic_t *atomic, spinlock_t *lock) int atomic_dec_and_lock(atomic_t *atomic, spinlock_t *lock)
{ {
int counter; int counter;
int newcount; int newcount;
repeat: for (;;) {
counter = atomic_read(atomic); counter = atomic_read(atomic);
newcount = counter-1; newcount = counter - 1;
if (!newcount)
if (!newcount) break; /* do it the slow way */
goto slow_path;
newcount = cmpxchg(&atomic->counter, counter, newcount); newcount = cmpxchg(&atomic->counter, counter, newcount);
if (newcount == counter)
return 0;
}
if (newcount != counter)
goto repeat;
return 0;
slow_path:
spin_lock(lock); spin_lock(lock);
if (atomic_dec_and_test(atomic)) if (atomic_dec_and_test(atomic))
return 1; return 1;
spin_unlock(lock); spin_unlock(lock);
return 0; return 0;
} }
EXPORT_SYMBOL(atomic_dec_and_lock);
#endif /* ATOMIC_DEC_AND_LOCK */
...@@ -33,6 +33,7 @@ static inline void __delay(unsigned long loops) ...@@ -33,6 +33,7 @@ static inline void __delay(unsigned long loops)
while((__get_tb()-start) < loops) while((__get_tb()-start) < loops)
__HMT_low(); __HMT_low();
__HMT_medium();
} }
static inline void udelay(unsigned long usecs) static inline void udelay(unsigned long usecs)
...@@ -40,7 +41,6 @@ static inline void udelay(unsigned long usecs) ...@@ -40,7 +41,6 @@ static inline void udelay(unsigned long usecs)
unsigned long loops = tb_ticks_per_usec * usecs; unsigned long loops = tb_ticks_per_usec * usecs;
__delay(loops); __delay(loops);
__HMT_medium();
} }
#endif /* _PPC64_DELAY_H */ #endif /* _PPC64_DELAY_H */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment