[PATCH] printk: Try to describe real console_sem dependecies using the crosslock feature

From: Petr Mladek
Date: Fri Nov 24 2017 - 10:50:25 EST


console_sem might be newly taken and released by different
processes. This is an attempt to check the crossrelease
dependencies.
---
kernel/printk/printk.c | 25 +++++++++----------------
1 file changed, 9 insertions(+), 16 deletions(-)

diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c
index 040fb948924e..bda25feae0d5 100644
--- a/kernel/printk/printk.c
+++ b/kernel/printk/printk.c
@@ -83,9 +83,9 @@ struct console *console_drivers;
EXPORT_SYMBOL_GPL(console_drivers);

#ifdef CONFIG_LOCKDEP
-static struct lockdep_map console_lock_dep_map = {
- .name = "console_lock"
-};
+static struct lockdep_map_cross console_lock_dep_map =
+ STATIC_CROSS_LOCKDEP_MAP_INIT("console_lock", &console_sem);
+
static struct lockdep_map console_owner_dep_map = {
.name = "console_owner"
};
@@ -218,7 +218,7 @@ static int nr_ext_console_drivers;
*/
#define down_console_sem() do { \
down(&console_sem);\
- mutex_acquire(&console_lock_dep_map, 0, 0, _RET_IP_);\
+ mutex_acquire((struct lockdep_map *)&console_lock_dep_map, 0, 0, _RET_IP_);\
} while (0)

static int __down_trylock_console_sem(unsigned long ip)
@@ -237,7 +237,7 @@ static int __down_trylock_console_sem(unsigned long ip)

if (lock_failed)
return 1;
- mutex_acquire(&console_lock_dep_map, 0, 1, ip);
+ mutex_acquire((struct lockdep_map *)&console_lock_dep_map, 0, 1, ip);
return 0;
}
#define down_trylock_console_sem() __down_trylock_console_sem(_RET_IP_)
@@ -246,7 +246,7 @@ static void __up_console_sem(unsigned long ip)
{
unsigned long flags;

- mutex_release(&console_lock_dep_map, 1, ip);
+ mutex_release((struct lockdep_map *)&console_lock_dep_map, 1, ip);

printk_safe_enter_irqsave(flags);
up(&console_sem);
@@ -1797,13 +1797,6 @@ asmlinkage int vprintk_emit(int facility, int level,
spin_release(&console_owner_dep_map, 1, _THIS_IP_);
printk_safe_exit_irqrestore(flags);

- /*
- * The owner passed the console lock to us.
- * Since we did not spin on console lock, annotate
- * this as a trylock. Otherwise lockdep will
- * complain.
- */
- mutex_acquire(&console_lock_dep_map, 0, 1, _THIS_IP_);
console_unlock();
printk_safe_enter_irqsave(flags);
}
@@ -2334,10 +2327,10 @@ void console_unlock(void)
/* The waiter is now free to continue */
spin_release(&console_owner_dep_map, 1, _THIS_IP_);
/*
- * Hand off console_lock to waiter. The waiter will perform
- * the up(). After this, the waiter is the console_lock owner.
+ * Hand off console_lock to waiter. After this, the waiter
+ * is the console_lock owner.
*/
- mutex_release(&console_lock_dep_map, 1, _THIS_IP_);
+ lock_commit_crosslock((struct lockdep_map *)&console_lock_dep_map);
printk_safe_exit_irqrestore(flags);
/* Note, if waiter is set, logbuf_lock is not held */
return;
--
2.13.6