summaryrefslogtreecommitdiff
path: root/kernel/printk
diff options
context:
space:
mode:
authorSasha Levin <sashal@kernel.org>2018-12-13 09:24:35 -0500
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2018-12-17 09:28:54 +0100
commit62582f67ff7617313b27b897ed02b569b712dcac (patch)
tree15a90baaa5bedf28ca68afccafb381987d956930 /kernel/printk
parent56926f913bf8284f0d33d79cdf0421f0caec8a1f (diff)
Revert "printk: Never set console_may_schedule in console_trylock()"
This reverts commit c9b8d580b3fb0ab65d37c372aef19a318fda3199. This is just a technical revert to make the printk fix apply cleanly, this patch will be re-picked in about 3 commits.
Diffstat (limited to 'kernel/printk')
-rw-r--r--kernel/printk/printk.c22
1 files changed, 14 insertions, 8 deletions
diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c
index a9cf2e15f6a3..7161312593dd 100644
--- a/kernel/printk/printk.c
+++ b/kernel/printk/printk.c
@@ -1763,19 +1763,12 @@ asmlinkage int vprintk_emit(int facility, int level,
/* If called from the scheduler, we can not call up(). */
if (!in_sched) {
/*
- * Disable preemption to avoid being preempted while holding
- * console_sem which would prevent anyone from printing to
- * console
- */
- preempt_disable();
- /*
* Try to acquire and then immediately release the console
* semaphore. The release will print out buffers and wake up
* /dev/kmsg and syslog() users.
*/
if (console_trylock())
console_unlock();
- preempt_enable();
}
return printed_len;
@@ -2090,7 +2083,20 @@ int console_trylock(void)
return 0;
}
console_locked = 1;
- console_may_schedule = 0;
+ /*
+ * When PREEMPT_COUNT disabled we can't reliably detect if it's
+ * safe to schedule (e.g. calling printk while holding a spin_lock),
+ * because preempt_disable()/preempt_enable() are just barriers there
+ * and preempt_count() is always 0.
+ *
+ * RCU read sections have a separate preemption counter when
+ * PREEMPT_RCU enabled thus we must take extra care and check
+ * rcu_preempt_depth(), otherwise RCU read sections modify
+ * preempt_count().
+ */
+ console_may_schedule = !oops_in_progress &&
+ preemptible() &&
+ !rcu_preempt_depth();
return 1;
}
EXPORT_SYMBOL(console_trylock);