Embedded Freedom
• source navigation • diff markup • identifier search • freetext search •
1 /* 2 * kernel/mutex-debug.c 3 * 4 * Debugging code for mutexes 5 * 6 * Started by Ingo Molnar: 7 * 8 * Copyright (C) 2004, 2005, 2006 Red Hat, Inc., Ingo Molnar <mingo@redhat.com> 9 * 10 * lock debugging, locking tree, deadlock detection started by: 11 * 12 * Copyright (C) 2004, LynuxWorks, Inc., Igor Manyilov, Bill Huey 13 * Released under the General Public License (GPL). 14 */ 15 #include <linux/mutex.h> 16 #include <linux/delay.h> 17 #include <linux/module.h> 18 #include <linux/poison.h> 19 #include <linux/spinlock.h> 20 #include <linux/kallsyms.h> 21 #include <linux/interrupt.h> 22 #include <linux/debug_locks.h> 23 24 #include "mutex-debug.h" 25 26 /* 27 * Must be called with lock->wait_lock held. 28 */ 29 void debug_mutex_set_owner(struct mutex *lock, struct thread_info *new_owner) 30 { 31 lock->owner = new_owner; 32 } 33 34 void debug_mutex_lock_common(struct mutex *lock, struct mutex_waiter *waiter) 35 { 36 memset(waiter, MUTEX_DEBUG_INIT, sizeof(*waiter)); 37 waiter->magic = waiter; 38 INIT_LIST_HEAD(&waiter->list); 39 } 40 41 void debug_mutex_wake_waiter(struct mutex *lock, struct mutex_waiter *waiter) 42 { 43 SMP_DEBUG_LOCKS_WARN_ON(!spin_is_locked(&lock->wait_lock)); 44 DEBUG_LOCKS_WARN_ON(list_empty(&lock->wait_list)); 45 DEBUG_LOCKS_WARN_ON(waiter->magic != waiter); 46 DEBUG_LOCKS_WARN_ON(list_empty(&waiter->list)); 47 } 48 49 void debug_mutex_free_waiter(struct mutex_waiter *waiter) 50 { 51 DEBUG_LOCKS_WARN_ON(!list_empty(&waiter->list)); 52 memset(waiter, MUTEX_DEBUG_FREE, sizeof(*waiter)); 53 } 54 55 void debug_mutex_add_waiter(struct mutex *lock, struct mutex_waiter *waiter, 56 struct thread_info *ti) 57 { 58 SMP_DEBUG_LOCKS_WARN_ON(!spin_is_locked(&lock->wait_lock)); 59 60 /* Mark the current thread as blocked on the lock: */ 61 ti->task->blocked_on = waiter; 62 waiter->lock = lock; 63 } 64 65 void mutex_remove_waiter(struct mutex *lock, struct mutex_waiter *waiter, 66 struct thread_info *ti) 67 { 68 DEBUG_LOCKS_WARN_ON(list_empty(&waiter->list)); 69 DEBUG_LOCKS_WARN_ON(waiter->task != ti->task); 70 DEBUG_LOCKS_WARN_ON(ti->task->blocked_on != waiter); 71 ti->task->blocked_on = NULL; 72 73 list_del_init(&waiter->list); 74 waiter->task = NULL; 75 } 76 77 void debug_mutex_unlock(struct mutex *lock) 78 { 79 if (unlikely(!debug_locks)) 80 return; 81 82 DEBUG_LOCKS_WARN_ON(lock->magic != lock); 83 DEBUG_LOCKS_WARN_ON(lock->owner != current_thread_info()); 84 DEBUG_LOCKS_WARN_ON(!lock->wait_list.prev && !lock->wait_list.next); 85 DEBUG_LOCKS_WARN_ON(lock->owner != current_thread_info()); 86 } 87 88 void debug_mutex_init(struct mutex *lock, const char *name, 89 struct lock_class_key *key) 90 { 91 #ifdef CONFIG_DEBUG_LOCK_ALLOC 92 /* 93 * Make sure we are not reinitializing a held lock: 94 */ 95 debug_check_no_locks_freed((void *)lock, sizeof(*lock)); 96 lockdep_init_map(&lock->dep_map, name, key, 0); 97 #endif 98 lock->owner = NULL; 99 lock->magic = lock; 100 } 101 102 /*** 103 * mutex_destroy - mark a mutex unusable 104 * @lock: the mutex to be destroyed 105 * 106 * This function marks the mutex uninitialized, and any subsequent 107 * use of the mutex is forbidden. The mutex must not be locked when 108 * this function is called. 109 */ 110 void mutex_destroy(struct mutex *lock) 111 { 112 DEBUG_LOCKS_WARN_ON(mutex_is_locked(lock)); 113 lock->magic = NULL; 114 } 115 116 EXPORT_SYMBOL_GPL(mutex_destroy); 117
This page was automatically generated by LXR 0.3.1. • Linux is a registered trademark of Linus Torvalds