locking changes for v3.9
Subsystems (10)
Linus,
Please pull the latest core-locking-for-linus git tree from:
git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git core-locking-for-linus
HEAD: 41ef8f826692c8f65882bec0a8211bd4d1d2d19a rwsem-spinlock: Implement writer lock-stealing for better scalability
The biggest change is the rwsem lock-steal improvements, both to the assembly optimized and the spinlock based variants.
The other notable change is the clean up of the seqlock implementation to be based on the seqcount infrastructure.
The rest is assorted smaller debuggability, cleanup and continued -rt locking changes.
Thanks,
Ingo
------------------>
Alex Shi (1):
rwsem: Implement writer lock-stealing for better scalability
Ben Greear (1):
lockdep: Print more info when MAX_LOCK_DEPTH is exceeded
Ingo Molnar (1):
generic: Use raw local irq variant for generic cmpxchg
Mike Galbraith (1):
intel_idle: Convert i7300_idle_lock to raw_spinlock
Namhyung Kim (1):
watchdog: Use local_clock for get_timestamp()
Paul Bolle (1):
lockdep: Silence warning if CONFIG_LOCKDEP isn't set
Srivatsa S. Bhat (1):
lockdep: Rename print_unlock_inbalance_bug() to print_unlock_imbalance_bug()
Thomas Gleixner (5):
locking: Various static lock initializer fixes
ntp: Make ntp_lock raw
seqlock: Remove unused functions
seqlock: Use seqcount infrastructure
futex: Revert "futex: Mark get_robust_list as deprecated"
Yong Zhang (1):
lockdep: Selftest: convert spinlock to raw spinlock
Yuanhan Liu (2):
locking/stat: Fix a typo
rwsem-spinlock: Implement writer lock-stealing for better scalability
Documentation/lockstat.txt | 2 +- drivers/char/random.c | 6 +- drivers/idle/i7300_idle.c | 8 +- drivers/usb/chipidea/debug.c | 2 +- fs/file.c | 2 +- include/asm-generic/cmpxchg-local.h | 8 +- include/linux/idr.h | 2 +- include/linux/lockdep.h | 2 +- include/linux/seqlock.h | 193 +++++++++++++++++------------------- kernel/futex.c | 2 - kernel/futex_compat.c | 2 - kernel/lockdep.c | 15 ++- kernel/time/ntp.c | 26 ++--- kernel/watchdog.c | 10 +- lib/locking-selftest.c | 34 +++---- lib/rwsem-spinlock.c | 69 +++++-------- lib/rwsem.c | 75 ++++++++------ 17 files changed, 221 insertions(+), 237 deletions(-)
Documentation/lockstat.txt +1 -1
@@ -65,7 +65,7 @@ that had to wait on lock acquisition. - CONFIGURATION -Lock statistics are enabled via CONFIG_LOCK_STATS. +Lock statistics are enabled via CONFIG_LOCK_STAT. - USAGE
drivers/char/random.c +3 -3
@@ -445,7 +445,7 @@ static struct entropy_store input_pool = { .poolinfo = &poolinfo_table[0], .name = "input", .limit = 1, - .lock = __SPIN_LOCK_UNLOCKED(&input_pool.lock), + .lock = __SPIN_LOCK_UNLOCKED(input_pool.lock), .pool = input_pool_data };
@@ -454,7 +454,7 @@ static struct entropy_store blocking_pool = { .name = "blocking", .limit = 1, .pull = &input_pool, - .lock = __SPIN_LOCK_UNLOCKED(&blocking_pool.lock), + .lock = __SPIN_LOCK_UNLOCKED(blocking_pool.lock), .pool = blocking_pool_data };
@@ -462,7 +462,7 @@ static struct entropy_store nonblocking_pool = { .poolinfo = &poolinfo_table[1], .name = "nonblocking", .pull = &input_pool, - .lock = __SPIN_LOCK_UNLOCKED(&nonblocking_pool.lock), + .lock = __SPIN_LOCK_UNLOCKED(nonblocking_pool.lock), .pool = nonblocking_pool_data };
drivers/idle/i7300_idle.c +4 -4
@@ -75,7 +75,7 @@ static unsigned long past_skip;static struct pci_dev *fbd_dev; -static spinlock_t i7300_idle_lock; +static raw_spinlock_t i7300_idle_lock;static int i7300_idle_active;static u8 i7300_idle_thrtctl_saved;
@@ -457,7 +457,7 @@ static int i7300_idle_notifier(struct notifier_block *nb, unsigned long val, idle_begin_time =ktime_get (); } -spin_lock_irqsave (&i7300_idle_lock, flags); +raw_spin_lock_irqsave (&i7300_idle_lock, flags);if (val ==IDLE_START ) {cpumask_set_cpu (smp_processor_id (), idle_cpumask);
@@ -506,7 +506,7 @@ static int i7300_idle_notifier(struct notifier_block *nb, unsigned long val, } } end: -spin_unlock_irqrestore (&i7300_idle_lock, flags); +raw_spin_unlock_irqrestore (&i7300_idle_lock, flags);return 0 ; }
@@ -548,7 +548,7 @@ struct debugfs_file_info {static int __init i7300_idle_init (void ) { -spin_lock_init (&i7300_idle_lock); +raw_spin_lock_init (&i7300_idle_lock); total_us =0 ;if (i7300_idle_platform_probe (&fbd_dev, &ioat_dev, forceload))
drivers/usb/chipidea/debug.c +1 -1
@@ -222,7 +222,7 @@ static struct { } dbg_data = { .idx = 0, .tty = 0, - .lck =__RW_LOCK_UNLOCKED (lck) + .lck =__RW_LOCK_UNLOCKED (dbg_data.lck) };/**
fs/file.c +1 -1
@@ -516,7 +516,7 @@ struct files_struct init_files = { .close_on_exec = init_files.close_on_exec_init, .open_fds = init_files.open_fds_init, }, - .file_lock = __SPIN_LOCK_UNLOCKED(init_task.file_lock), + .file_lock = __SPIN_LOCK_UNLOCKED(init_files.file_lock), };/*
include/asm-generic/cmpxchg-local.h +4 -4
@@ -21,7 +21,7 @@ static inline unsigned long __cmpxchg_local_generic(volatile void *ptr,if (size ==8 &&sizeof (unsigned long ) !=8 )wrong_size_cmpxchg (ptr); -local_irq_save (flags); +raw_local_irq_save (flags);switch (size) {case 1 : prev = *(u8 *)ptr;if (prev == old)
@@ -42,7 +42,7 @@ static inline unsigned long __cmpxchg_local_generic(volatile void *ptr,default :wrong_size_cmpxchg (ptr); } -local_irq_restore (flags); +raw_local_irq_restore (flags);return prev; }
@@ -55,11 +55,11 @@ static inline u64 __cmpxchg64_local_generic(volatile void *ptr,u64 prev;unsigned long flags; -local_irq_save (flags); +raw_local_irq_save (flags); prev = *(u64 *)ptr;if (prev == old) *(u64 *)ptr = new; -local_irq_restore (flags); +raw_local_irq_restore (flags);return prev; }
include/linux/idr.h +1 -1
@@ -136,7 +136,7 @@ struct ida {struct ida_bitmap *free_bitmap; }; -#define IDA_INIT (name) { .idr = IDR_INIT(name), .free_bitmap = NULL, } +#define IDA_INIT (name) { .idr = IDR_INIT((name).idr), .free_bitmap = NULL, }#define DEFINE_IDA (name) struct ida name = IDA_INIT(name)int ida_pre_get (struct ida *ida,gfp_t gfp_mask);
include/linux/lockdep.h +1 -1
@@ -410,7 +410,7 @@ struct lock_class_key { };#define lockdep_depth (tsk) (0) -#define lockdep_assert_held (l) do { } while (0) +#define lockdep_assert_held (l) do { (void)(l); } while (0)#define lockdep_recursing (tsk) (0)
include/linux/seqlock.h +91 -102
221 lines not on this page · raw message
kernel/futex.c +0 -2
@@ -2471,8 +2471,6 @@ SYSCALL_DEFINE3(get_robust_list, int, pid,if (!futex_cmpxchg_enabled)return -ENOSYS ; -WARN_ONCE (1 ,"deprecated: get_robust_list will be deleted in 2013.\n" ); -rcu_read_lock (); ret = -ESRCH ;
kernel/futex_compat.c +0 -2
@@ -142,8 +142,6 @@ compat_sys_get_robust_list(int pid, compat_uptr_t __user *head_ptr,if (!futex_cmpxchg_enabled)return -ENOSYS ; -WARN_ONCE (1 ,"deprecated: get_robust_list will be deleted in 2013.\n" ); -rcu_read_lock (); ret = -ESRCH ;
kernel/lockdep.c +10 -5
@@ -3190,9 +3190,14 @@ static int __lock_acquire(struct lockdep_map *lock, unsigned int subclass,#endif if (unlikely (curr->lockdep_depth >=MAX_LOCK_DEPTH )) {debug_locks_off (); -printk ("BUG: MAX_LOCK_DEPTH too low!\n" ); +printk ("BUG: MAX_LOCK_DEPTH too low, depth: %i max: %lu!\n" , + curr->lockdep_depth,MAX_LOCK_DEPTH );printk ("turning off the locking correctness validator.\n" ); + +lockdep_print_held_locks (current); +debug_show_all_locks ();dump_stack (); +return 0 ; }
@@ -3203,7 +3208,7 @@ static int __lock_acquire(struct lockdep_map *lock, unsigned int subclass, }static int -print_unlock_inbalance_bug (struct task_struct *curr,struct lockdep_map *lock, +print_unlock_imbalance_bug (struct task_struct *curr,struct lockdep_map *lock,unsigned long ip) {if (!debug_locks_off ())
@@ -3246,7 +3251,7 @@ static int check_unlock(struct task_struct *curr, struct lockdep_map *lock,return 0 ;if (curr->lockdep_depth <=0 ) -return print_unlock_inbalance_bug (curr, lock, ip); +return print_unlock_imbalance_bug (curr, lock, ip);return 1 ; }
@@ -3317,7 +3322,7 @@ __lock_set_class(struct lockdep_map *lock, const char *name, goto found_it; prev_hlock = hlock; } -return print_unlock_inbalance_bug (curr, lock, ip); +return print_unlock_imbalance_bug (curr, lock, ip); found_it:lockdep_init_map (lock, name, key,0 );
@@ -3384,7 +3389,7 @@ lock_release_non_nested(struct task_struct *curr, goto found_it; prev_hlock = hlock; } -return print_unlock_inbalance_bug (curr, lock, ip); +return print_unlock_imbalance_bug (curr, lock, ip); found_it:if (hlock->instance == lock)
kernel/time/ntp.c +13 -13
@@ -22,7 +22,7 @@* NTP timekeeping variables: */ -DEFINE_SPINLOCK (ntp_lock); +DEFINE_RAW_SPINLOCK (ntp_lock);/* USER_HZ period (usecs): */
@@ -347,7 +347,7 @@ void ntp_clear(void) {unsigned long flags; -spin_lock_irqsave (&ntp_lock, flags); +raw_spin_lock_irqsave (&ntp_lock, flags); time_adjust =0 ;/* stop active adjtime() */ time_status |=STA_UNSYNC ;
@@ -361,7 +361,7 @@ void ntp_clear(void)/* Clear PPS state variables */ pps_clear (); -spin_unlock_irqrestore (&ntp_lock, flags); +raw_spin_unlock_irqrestore (&ntp_lock, flags); }
@@ -371,9 +371,9 @@ u64 ntp_tick_length(void)unsigned long flags;s64 ret; -spin_lock_irqsave (&ntp_lock, flags); +raw_spin_lock_irqsave (&ntp_lock, flags); ret = tick_length; -spin_unlock_irqrestore (&ntp_lock, flags); +raw_spin_unlock_irqrestore (&ntp_lock, flags);return ret; }
@@ -394,7 +394,7 @@ int second_overflow(unsigned long secs)int leap =0 ;unsigned long flags; -spin_lock_irqsave (&ntp_lock, flags); +raw_spin_lock_irqsave (&ntp_lock, flags);/* * Leap second processing. If in leap-insert state at the end of the
@@ -478,7 +478,7 @@ int second_overflow(unsigned long secs) time_adjust =0 ; out: -spin_unlock_irqrestore (&ntp_lock, flags); +raw_spin_unlock_irqrestore (&ntp_lock, flags);return leap; }
@@ -660,7 +660,7 @@ int do_adjtimex(struct timex *txc)getnstimeofday (&ts); -spin_lock_irq (&ntp_lock); +raw_spin_lock_irq (&ntp_lock);if (txc->modes &ADJ_ADJTIME ) {long save_adjust = time_adjust;
@@ -702,7 +702,7 @@ int do_adjtimex(struct timex *txc)/* fill PPS status fields */ pps_fill_timex (txc); -spin_unlock_irq (&ntp_lock); +raw_spin_unlock_irq (&ntp_lock); txc->time.tv_sec = ts.tv_sec; txc->time.tv_usec = ts.tv_nsec;
@@ -900,7 +900,7 @@ void hardpps(const struct timespec *phase_ts, const struct timespec *raw_ts) pts_norm =pps_normalize_ts (*phase_ts); -spin_lock_irqsave (&ntp_lock, flags); +raw_spin_lock_irqsave (&ntp_lock, flags);/* clear the error bits, they will be set again if needed */ time_status &= ~(STA_PPSJITTER |STA_PPSWANDER |STA_PPSERROR );
@@ -913,7 +913,7 @@ void hardpps(const struct timespec *phase_ts, const struct timespec *raw_ts)* just start the frequency interval */ if (unlikely (pps_fbase.tv_sec ==0 )) { pps_fbase = *raw_ts; -spin_unlock_irqrestore (&ntp_lock, flags); +raw_spin_unlock_irqrestore (&ntp_lock, flags);return ; }
@@ -928,7 +928,7 @@ void hardpps(const struct timespec *phase_ts, const struct timespec *raw_ts) time_status |=STA_PPSJITTER ;/* restart the frequency calibration interval */ pps_fbase = *raw_ts; -spin_unlock_irqrestore (&ntp_lock, flags); +raw_spin_unlock_irqrestore (&ntp_lock, flags);pr_err ("hardpps: PPSJITTER: bad pulse\n" );return ; }
@@ -945,7 +945,7 @@ void hardpps(const struct timespec *phase_ts, const struct timespec *raw_ts)hardpps_update_phase (pts_norm.nsec); -spin_unlock_irqrestore (&ntp_lock, flags); +raw_spin_unlock_irqrestore (&ntp_lock, flags); }EXPORT_SYMBOL (hardpps);
kernel/watchdog.c +4 -6
@@ -112,9 +112,9 @@ static int get_softlockup_thresh(void)* resolution, and we don't need to waste time with a big divide when * 2^30ns == 1.074s. */ -static unsigned long get_timestamp (int this_cpu) +static unsigned long get_timestamp (void ) { -return cpu_clock (this_cpu) >>30LL ;/* 2^30 ~= 10^9 */ +return local_clock () >>30LL ;/* 2^30 ~= 10^9 */ }static void set_sample_period (void )
@@ -132,9 +132,7 @@ static void set_sample_period(void)/* Commands for resetting the watchdog */ static void __touch_watchdog (void ) { -int this_cpu =smp_processor_id (); - -__this_cpu_write (watchdog_touch_ts,get_timestamp (this_cpu)); +__this_cpu_write (watchdog_touch_ts,get_timestamp ()); }void touch_softlockup_watchdog (void )
@@ -195,7 +193,7 @@ static int is_hardlockup(void)static int is_softlockup (unsigned long touch_ts) { -unsigned long now =get_timestamp (smp_processor_id ()); +unsigned long now =get_timestamp ();/* Warn about unreasonable delays: */ if (time_after (now, touch_ts +get_softlockup_thresh ()))
lib/locking-selftest.c +17 -17
@@ -47,10 +47,10 @@ __setup("debug_locks_verbose=", setup_debug_locks_verbose);* Normal standalone locks, for the circular and irq-context * dependency tests: */ -static DEFINE_SPINLOCK (lock_A); -static DEFINE_SPINLOCK (lock_B); -static DEFINE_SPINLOCK (lock_C); -static DEFINE_SPINLOCK (lock_D); +static DEFINE_RAW_SPINLOCK (lock_A); +static DEFINE_RAW_SPINLOCK (lock_B); +static DEFINE_RAW_SPINLOCK (lock_C); +static DEFINE_RAW_SPINLOCK (lock_D);static DEFINE_RWLOCK (rwlock_A);static DEFINE_RWLOCK (rwlock_B);
@@ -73,12 +73,12 @@ static DECLARE_RWSEM(rwsem_D);* but X* and Y* are different classes. We do this so that * we do not trigger a real lockup: */ -static DEFINE_SPINLOCK (lock_X1); -static DEFINE_SPINLOCK (lock_X2); -static DEFINE_SPINLOCK (lock_Y1); -static DEFINE_SPINLOCK (lock_Y2); -static DEFINE_SPINLOCK (lock_Z1); -static DEFINE_SPINLOCK (lock_Z2); +static DEFINE_RAW_SPINLOCK (lock_X1); +static DEFINE_RAW_SPINLOCK (lock_X2); +static DEFINE_RAW_SPINLOCK (lock_Y1); +static DEFINE_RAW_SPINLOCK (lock_Y2); +static DEFINE_RAW_SPINLOCK (lock_Z1); +static DEFINE_RAW_SPINLOCK (lock_Z2);static DEFINE_RWLOCK (rwlock_X1);static DEFINE_RWLOCK (rwlock_X2);
@@ -107,10 +107,10 @@ static DECLARE_RWSEM(rwsem_Z2);*/ #define INIT_CLASS_FUNC (class) \ static noinline void \ -init_class_##class(spinlock_t *lock, rwlock_t *rwlock, struct mutex *mutex, \ - struct rw_semaphore *rwsem) \ +init_class_##class(raw_spinlock_t *lock, rwlock_t *rwlock, \ + struct mutex *mutex, struct rw_semaphore *rwsem)\ { \ - spin_lock_init(lock); \ + raw_spin_lock_init(lock); \ rwlock_init(rwlock); \ mutex_init(mutex); \ init_rwsem(rwsem); \
@@ -168,10 +168,10 @@ static void init_shared_classes(void)* Shortcuts for lock/unlock API variants, to keep * the testcases compact: */ -#define L (x) spin_lock(&lock_##x) -#define U (x) spin_unlock(&lock_##x) +#define L (x) raw_spin_lock(&lock_##x) +#define U (x) raw_spin_unlock(&lock_##x)#define LU (x) L(x); U(x) -#define SI (x) spin_lock_init(&lock_##x) +#define SI (x) raw_spin_lock_init(&lock_##x)#define WL (x) write_lock(&rwlock_##x)#define WU (x) write_unlock(&rwlock_##x)
@@ -911,7 +911,7 @@ GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_soft)#define I2 (x) \ do { \ - spin_lock_init(&lock_##x); \ + raw_spin_lock_init(&lock_##x); \ rwlock_init(&rwlock_##x); \ mutex_init(&mutex_##x); \ init_rwsem(&rwsem_##x); \
lib/rwsem-spinlock.c +24 -45
114 lines not on this page · raw message
lib/rwsem.c +46 -29
107 lines not on this page · raw message