Line data Source code
1 : // SPDX-License-Identifier: GPL-2.0
2 : /*
3 : * RT-Mutexes: blocking mutual exclusion locks with PI support
4 : *
5 : * started by Ingo Molnar and Thomas Gleixner:
6 : *
7 : * Copyright (C) 2004-2006 Red Hat, Inc., Ingo Molnar <mingo@redhat.com>
8 : * Copyright (C) 2006 Timesys Corp., Thomas Gleixner <tglx@timesys.com>
9 : *
10 : * This code is based on the rt.c implementation in the preempt-rt tree.
11 : * Portions of said code are
12 : *
13 : * Copyright (C) 2004 LynuxWorks, Inc., Igor Manyilov, Bill Huey
14 : * Copyright (C) 2006 Esben Nielsen
15 : * Copyright (C) 2006 Kihon Technologies Inc.,
16 : * Steven Rostedt <rostedt@goodmis.org>
17 : *
18 : * See rt.c in preempt-rt for proper credits and further information
19 : */
20 : #include <linux/sched.h>
21 : #include <linux/sched/rt.h>
22 : #include <linux/sched/debug.h>
23 : #include <linux/delay.h>
24 : #include <linux/export.h>
25 : #include <linux/spinlock.h>
26 : #include <linux/kallsyms.h>
27 : #include <linux/syscalls.h>
28 : #include <linux/interrupt.h>
29 : #include <linux/rbtree.h>
30 : #include <linux/fs.h>
31 : #include <linux/debug_locks.h>
32 :
33 : #include "rtmutex_common.h"
34 :
35 0 : static void printk_task(struct task_struct *p)
36 : {
37 0 : if (p)
38 0 : printk("%16s:%5d [%p, %3d]", p->comm, task_pid_nr(p), p, p->prio);
39 : else
40 0 : printk("<none>");
41 0 : }
42 :
43 0 : static void printk_lock(struct rt_mutex *lock, int print_owner)
44 : {
45 0 : if (lock->name)
46 0 : printk(" [%p] {%s}\n",
47 : lock, lock->name);
48 : else
49 0 : printk(" [%p] {%s:%d}\n",
50 : lock, lock->file, lock->line);
51 :
52 0 : if (print_owner && rt_mutex_owner(lock)) {
53 0 : printk(".. ->owner: %p\n", lock->owner);
54 0 : printk(".. held by: ");
55 0 : printk_task(rt_mutex_owner(lock));
56 0 : printk("\n");
57 : }
58 0 : }
59 :
60 960 : void rt_mutex_debug_task_free(struct task_struct *task)
61 : {
62 960 : DEBUG_LOCKS_WARN_ON(!RB_EMPTY_ROOT(&task->pi_waiters.rb_root));
63 960 : DEBUG_LOCKS_WARN_ON(task->pi_blocked_on);
64 960 : }
65 :
66 : /*
67 : * We fill out the fields in the waiter to store the information about
68 : * the deadlock. We print when we return. act_waiter can be NULL in
69 : * case of a remove waiter operation.
70 : */
71 0 : void debug_rt_mutex_deadlock(enum rtmutex_chainwalk chwalk,
72 : struct rt_mutex_waiter *act_waiter,
73 : struct rt_mutex *lock)
74 : {
75 0 : struct task_struct *task;
76 :
77 0 : if (!debug_locks || chwalk == RT_MUTEX_FULL_CHAINWALK || !act_waiter)
78 : return;
79 :
80 0 : task = rt_mutex_owner(act_waiter->lock);
81 0 : if (task && task != current) {
82 0 : act_waiter->deadlock_task_pid = get_pid(task_pid(task));
83 0 : act_waiter->deadlock_lock = lock;
84 : }
85 : }
86 :
87 0 : void debug_rt_mutex_print_deadlock(struct rt_mutex_waiter *waiter)
88 : {
89 0 : struct task_struct *task;
90 :
91 0 : if (!waiter->deadlock_lock || !debug_locks)
92 : return;
93 :
94 0 : rcu_read_lock();
95 0 : task = pid_task(waiter->deadlock_task_pid, PIDTYPE_PID);
96 0 : if (!task) {
97 0 : rcu_read_unlock();
98 0 : return;
99 : }
100 :
101 0 : if (!debug_locks_off()) {
102 0 : rcu_read_unlock();
103 0 : return;
104 : }
105 :
106 0 : pr_warn("\n");
107 0 : pr_warn("============================================\n");
108 0 : pr_warn("WARNING: circular locking deadlock detected!\n");
109 0 : pr_warn("%s\n", print_tainted());
110 0 : pr_warn("--------------------------------------------\n");
111 0 : printk("%s/%d is deadlocking current task %s/%d\n\n",
112 0 : task->comm, task_pid_nr(task),
113 0 : current->comm, task_pid_nr(current));
114 :
115 0 : printk("\n1) %s/%d is trying to acquire this lock:\n",
116 0 : current->comm, task_pid_nr(current));
117 0 : printk_lock(waiter->lock, 1);
118 :
119 0 : printk("\n2) %s/%d is blocked on this lock:\n",
120 : task->comm, task_pid_nr(task));
121 0 : printk_lock(waiter->deadlock_lock, 1);
122 :
123 0 : debug_show_held_locks(current);
124 0 : debug_show_held_locks(task);
125 :
126 0 : printk("\n%s/%d's [blocked] stackdump:\n\n",
127 : task->comm, task_pid_nr(task));
128 0 : show_stack(task, NULL, KERN_DEFAULT);
129 0 : printk("\n%s/%d's [current] stackdump:\n\n",
130 0 : current->comm, task_pid_nr(current));
131 0 : dump_stack();
132 0 : debug_show_all_locks();
133 0 : rcu_read_unlock();
134 :
135 0 : printk("[ turning off deadlock detection."
136 : "Please report this trace. ]\n\n");
137 : }
138 :
139 0 : void debug_rt_mutex_lock(struct rt_mutex *lock)
140 : {
141 0 : }
142 :
143 0 : void debug_rt_mutex_unlock(struct rt_mutex *lock)
144 : {
145 0 : DEBUG_LOCKS_WARN_ON(rt_mutex_owner(lock) != current);
146 0 : }
147 :
148 : void
149 0 : debug_rt_mutex_proxy_lock(struct rt_mutex *lock, struct task_struct *powner)
150 : {
151 0 : }
152 :
153 0 : void debug_rt_mutex_proxy_unlock(struct rt_mutex *lock)
154 : {
155 0 : DEBUG_LOCKS_WARN_ON(!rt_mutex_owner(lock));
156 0 : }
157 :
158 0 : void debug_rt_mutex_init_waiter(struct rt_mutex_waiter *waiter)
159 : {
160 0 : memset(waiter, 0x11, sizeof(*waiter));
161 0 : waiter->deadlock_task_pid = NULL;
162 0 : }
163 :
164 0 : void debug_rt_mutex_free_waiter(struct rt_mutex_waiter *waiter)
165 : {
166 0 : put_pid(waiter->deadlock_task_pid);
167 0 : memset(waiter, 0x22, sizeof(*waiter));
168 0 : }
169 :
170 0 : void debug_rt_mutex_init(struct rt_mutex *lock, const char *name, struct lock_class_key *key)
171 : {
172 : /*
173 : * Make sure we are not reinitializing a held lock:
174 : */
175 0 : debug_check_no_locks_freed((void *)lock, sizeof(*lock));
176 0 : lock->name = name;
177 :
178 : #ifdef CONFIG_DEBUG_LOCK_ALLOC
179 0 : lockdep_init_map(&lock->dep_map, name, key, 0);
180 : #endif
181 0 : }
182 :
|