aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/printk.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/printk.c')
-rw-r--r--kernel/printk.c24
1 files changed, 18 insertions, 6 deletions
diff --git a/kernel/printk.c b/kernel/printk.c
index 95b7fe17f124..bdba5d80496c 100644
--- a/kernel/printk.c
+++ b/kernel/printk.c
@@ -26,7 +26,6 @@
26#include <linux/module.h> 26#include <linux/module.h>
27#include <linux/moduleparam.h> 27#include <linux/moduleparam.h>
28#include <linux/interrupt.h> /* For in_interrupt() */ 28#include <linux/interrupt.h> /* For in_interrupt() */
29#include <linux/config.h>
30#include <linux/delay.h> 29#include <linux/delay.h>
31#include <linux/smp.h> 30#include <linux/smp.h>
32#include <linux/security.h> 31#include <linux/security.h>
@@ -519,7 +518,9 @@ asmlinkage int vprintk(const char *fmt, va_list args)
519 zap_locks(); 518 zap_locks();
520 519
521 /* This stops the holder of console_sem just where we want him */ 520 /* This stops the holder of console_sem just where we want him */
522 spin_lock_irqsave(&logbuf_lock, flags); 521 local_irq_save(flags);
522 lockdep_off();
523 spin_lock(&logbuf_lock);
523 printk_cpu = smp_processor_id(); 524 printk_cpu = smp_processor_id();
524 525
525 /* Emit the output into the temporary buffer */ 526 /* Emit the output into the temporary buffer */
@@ -589,7 +590,7 @@ asmlinkage int vprintk(const char *fmt, va_list args)
589 */ 590 */
590 console_locked = 1; 591 console_locked = 1;
591 printk_cpu = UINT_MAX; 592 printk_cpu = UINT_MAX;
592 spin_unlock_irqrestore(&logbuf_lock, flags); 593 spin_unlock(&logbuf_lock);
593 594
594 /* 595 /*
595 * Console drivers may assume that per-cpu resources have 596 * Console drivers may assume that per-cpu resources have
@@ -605,6 +606,8 @@ asmlinkage int vprintk(const char *fmt, va_list args)
605 console_locked = 0; 606 console_locked = 0;
606 up(&console_sem); 607 up(&console_sem);
607 } 608 }
609 lockdep_on();
610 local_irq_restore(flags);
608 } else { 611 } else {
609 /* 612 /*
610 * Someone else owns the drivers. We drop the spinlock, which 613 * Someone else owns the drivers. We drop the spinlock, which
@@ -612,7 +615,9 @@ asmlinkage int vprintk(const char *fmt, va_list args)
612 * console drivers with the output which we just produced. 615 * console drivers with the output which we just produced.
613 */ 616 */
614 printk_cpu = UINT_MAX; 617 printk_cpu = UINT_MAX;
615 spin_unlock_irqrestore(&logbuf_lock, flags); 618 spin_unlock(&logbuf_lock);
619 lockdep_on();
620 local_irq_restore(flags);
616 } 621 }
617 622
618 preempt_enable(); 623 preempt_enable();
@@ -810,8 +815,15 @@ void release_console_sem(void)
810 console_may_schedule = 0; 815 console_may_schedule = 0;
811 up(&console_sem); 816 up(&console_sem);
812 spin_unlock_irqrestore(&logbuf_lock, flags); 817 spin_unlock_irqrestore(&logbuf_lock, flags);
813 if (wake_klogd && !oops_in_progress && waitqueue_active(&log_wait)) 818 if (wake_klogd && !oops_in_progress && waitqueue_active(&log_wait)) {
814 wake_up_interruptible(&log_wait); 819 /*
820 * If we printk from within the lock dependency code,
821 * from within the scheduler code, then do not lock
822 * up due to self-recursion:
823 */
824 if (!lockdep_internal())
825 wake_up_interruptible(&log_wait);
826 }
815} 827}
816EXPORT_SYMBOL(release_console_sem); 828EXPORT_SYMBOL(release_console_sem);
817 829