aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/printk.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/printk.c')
-rw-r--r--kernel/printk.c57
1 files changed, 41 insertions, 16 deletions
diff --git a/kernel/printk.c b/kernel/printk.c
index 89011bf8c106..423a8c765a57 100644
--- a/kernel/printk.c
+++ b/kernel/printk.c
@@ -573,11 +573,6 @@ static int __init printk_time_setup(char *str)
573 573
574__setup("time", printk_time_setup); 574__setup("time", printk_time_setup);
575 575
576__attribute__((weak)) unsigned long long printk_clock(void)
577{
578 return sched_clock();
579}
580
581/* Check if we have any console registered that can be called early in boot. */ 576/* Check if we have any console registered that can be called early in boot. */
582static int have_callable_console(void) 577static int have_callable_console(void)
583{ 578{
@@ -628,30 +623,57 @@ asmlinkage int printk(const char *fmt, ...)
628/* cpu currently holding logbuf_lock */ 623/* cpu currently holding logbuf_lock */
629static volatile unsigned int printk_cpu = UINT_MAX; 624static volatile unsigned int printk_cpu = UINT_MAX;
630 625
626const char printk_recursion_bug_msg [] =
627 KERN_CRIT "BUG: recent printk recursion!\n";
628static int printk_recursion_bug;
629
631asmlinkage int vprintk(const char *fmt, va_list args) 630asmlinkage int vprintk(const char *fmt, va_list args)
632{ 631{
632 static int log_level_unknown = 1;
633 static char printk_buf[1024];
634
633 unsigned long flags; 635 unsigned long flags;
634 int printed_len; 636 int printed_len = 0;
637 int this_cpu;
635 char *p; 638 char *p;
636 static char printk_buf[1024];
637 static int log_level_unknown = 1;
638 639
639 boot_delay_msec(); 640 boot_delay_msec();
640 641
641 preempt_disable(); 642 preempt_disable();
642 if (unlikely(oops_in_progress) && printk_cpu == smp_processor_id())
643 /* If a crash is occurring during printk() on this CPU,
644 * make sure we can't deadlock */
645 zap_locks();
646
647 /* This stops the holder of console_sem just where we want him */ 643 /* This stops the holder of console_sem just where we want him */
648 raw_local_irq_save(flags); 644 raw_local_irq_save(flags);
645 this_cpu = smp_processor_id();
646
647 /*
648 * Ouch, printk recursed into itself!
649 */
650 if (unlikely(printk_cpu == this_cpu)) {
651 /*
652 * If a crash is occurring during printk() on this CPU,
653 * then try to get the crash message out but make sure
654 * we can't deadlock. Otherwise just return to avoid the
655 * recursion and return - but flag the recursion so that
656 * it can be printed at the next appropriate moment:
657 */
658 if (!oops_in_progress) {
659 printk_recursion_bug = 1;
660 goto out_restore_irqs;
661 }
662 zap_locks();
663 }
664
649 lockdep_off(); 665 lockdep_off();
650 spin_lock(&logbuf_lock); 666 spin_lock(&logbuf_lock);
651 printk_cpu = smp_processor_id(); 667 printk_cpu = this_cpu;
652 668
669 if (printk_recursion_bug) {
670 printk_recursion_bug = 0;
671 strcpy(printk_buf, printk_recursion_bug_msg);
672 printed_len = sizeof(printk_recursion_bug_msg);
673 }
653 /* Emit the output into the temporary buffer */ 674 /* Emit the output into the temporary buffer */
654 printed_len = vscnprintf(printk_buf, sizeof(printk_buf), fmt, args); 675 printed_len += vscnprintf(printk_buf + printed_len,
676 sizeof(printk_buf), fmt, args);
655 677
656 /* 678 /*
657 * Copy the output into log_buf. If the caller didn't provide 679 * Copy the output into log_buf. If the caller didn't provide
@@ -680,7 +702,9 @@ asmlinkage int vprintk(const char *fmt, va_list args)
680 loglev_char = default_message_loglevel 702 loglev_char = default_message_loglevel
681 + '0'; 703 + '0';
682 } 704 }
683 t = printk_clock(); 705 t = 0;
706 if (system_state != SYSTEM_BOOTING)
707 t = ktime_to_ns(ktime_get());
684 nanosec_rem = do_div(t, 1000000000); 708 nanosec_rem = do_div(t, 1000000000);
685 tlen = sprintf(tbuf, 709 tlen = sprintf(tbuf,
686 "<%c>[%5lu.%06lu] ", 710 "<%c>[%5lu.%06lu] ",
@@ -744,6 +768,7 @@ asmlinkage int vprintk(const char *fmt, va_list args)
744 printk_cpu = UINT_MAX; 768 printk_cpu = UINT_MAX;
745 spin_unlock(&logbuf_lock); 769 spin_unlock(&logbuf_lock);
746 lockdep_on(); 770 lockdep_on();
771out_restore_irqs:
747 raw_local_irq_restore(flags); 772 raw_local_irq_restore(flags);
748 } 773 }
749 774