X-Git-Url: http://git.onelab.eu/?a=blobdiff_plain;f=arch%2Fppc%2Flib%2Flocks.c;h=0eaffa9b59aefbcfdf7093bd34e917f8ec634517;hb=9213980e6a70d8473e0ffd4b39ab5b6caaba9ff5;hp=1f85f3ef2771a8f2a672f5e657d3462af01cb010;hpb=c449269f45c2cdf53af08c8d0af37472f66539d9;p=linux-2.6.git diff --git a/arch/ppc/lib/locks.c b/arch/ppc/lib/locks.c index 1f85f3ef2..0eaffa9b5 100644 --- a/arch/ppc/lib/locks.c +++ b/arch/ppc/lib/locks.c @@ -7,6 +7,7 @@ #include #include #include +#include #include #include @@ -22,7 +23,7 @@ * since they may inhibit forward progress by other CPUs in getting * a lock. */ -unsigned long __spin_trylock(volatile unsigned long *lock) +static inline unsigned long __spin_trylock(volatile unsigned long *lock) { unsigned long ret; @@ -62,6 +63,7 @@ void _raw_spin_lock(spinlock_t *lock) lock->owner_pc = (unsigned long)__builtin_return_address(0); lock->owner_cpu = cpu; } +EXPORT_SYMBOL(_raw_spin_lock); int _raw_spin_trylock(spinlock_t *lock) { @@ -71,6 +73,7 @@ int _raw_spin_trylock(spinlock_t *lock) lock->owner_pc = (unsigned long)__builtin_return_address(0); return 1; } +EXPORT_SYMBOL(_raw_spin_trylock); void _raw_spin_unlock(spinlock_t *lp) { @@ -86,6 +89,7 @@ void _raw_spin_unlock(spinlock_t *lp) wmb(); lp->lock = 0; } +EXPORT_SYMBOL(_raw_spin_unlock); /* @@ -119,6 +123,7 @@ again: } wmb(); } +EXPORT_SYMBOL(_raw_read_lock); void _raw_read_unlock(rwlock_t *rw) { @@ -129,6 +134,7 @@ void _raw_read_unlock(rwlock_t *rw) wmb(); atomic_dec((atomic_t *) &(rw)->lock); } +EXPORT_SYMBOL(_raw_read_unlock); void _raw_write_lock(rwlock_t *rw) { @@ -169,6 +175,22 @@ again: } wmb(); } +EXPORT_SYMBOL(_raw_write_lock); + +int _raw_write_trylock(rwlock_t *rw) +{ + if (test_and_set_bit(31, &(rw)->lock)) /* someone has a write lock */ + return 0; + + if ((rw)->lock & ~(1<<31)) { /* someone has a read lock */ + /* clear our write lock and wait for reads to go away */ + clear_bit(31,&(rw)->lock); + return 0; + } + wmb(); + return 1; +} +EXPORT_SYMBOL(_raw_write_trylock); void _raw_write_unlock(rwlock_t *rw) { @@ -179,5 +201,6 @@ void _raw_write_unlock(rwlock_t *rw) wmb(); clear_bit(31,&(rw)->lock); } +EXPORT_SYMBOL(_raw_write_unlock); #endif