|
@@ -1829,28 +1829,16 @@ static size_t log_output(int facility, int level, enum log_flags lflags, const c
|
|
return log_store(facility, level, lflags, 0, dict, dictlen, text, text_len);
|
|
return log_store(facility, level, lflags, 0, dict, dictlen, text, text_len);
|
|
}
|
|
}
|
|
|
|
|
|
-asmlinkage int vprintk_emit(int facility, int level,
|
|
|
|
- const char *dict, size_t dictlen,
|
|
|
|
- const char *fmt, va_list args)
|
|
|
|
|
|
+/* Must be called under logbuf_lock. */
|
|
|
|
+int vprintk_store(int facility, int level,
|
|
|
|
+ const char *dict, size_t dictlen,
|
|
|
|
+ const char *fmt, va_list args)
|
|
{
|
|
{
|
|
static char textbuf[LOG_LINE_MAX];
|
|
static char textbuf[LOG_LINE_MAX];
|
|
char *text = textbuf;
|
|
char *text = textbuf;
|
|
size_t text_len;
|
|
size_t text_len;
|
|
enum log_flags lflags = 0;
|
|
enum log_flags lflags = 0;
|
|
- unsigned long flags;
|
|
|
|
- int printed_len;
|
|
|
|
- bool in_sched = false;
|
|
|
|
-
|
|
|
|
- if (level == LOGLEVEL_SCHED) {
|
|
|
|
- level = LOGLEVEL_DEFAULT;
|
|
|
|
- in_sched = true;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- boot_delay_msec(level);
|
|
|
|
- printk_delay();
|
|
|
|
|
|
|
|
- /* This stops the holder of console_sem just where we want him */
|
|
|
|
- logbuf_lock_irqsave(flags);
|
|
|
|
/*
|
|
/*
|
|
* The printf needs to come first; we need the syslog
|
|
* The printf needs to come first; we need the syslog
|
|
* prefix which might be passed-in as a parameter.
|
|
* prefix which might be passed-in as a parameter.
|
|
@@ -1894,8 +1882,29 @@ asmlinkage int vprintk_emit(int facility, int level,
|
|
if (suppress_message_printing(level))
|
|
if (suppress_message_printing(level))
|
|
lflags |= LOG_NOCONS;
|
|
lflags |= LOG_NOCONS;
|
|
|
|
|
|
- printed_len = log_output(facility, level, lflags, dict, dictlen, text, text_len);
|
|
|
|
|
|
+ return log_output(facility, level, lflags,
|
|
|
|
+ dict, dictlen, text, text_len);
|
|
|
|
+}
|
|
|
|
|
|
|
|
+asmlinkage int vprintk_emit(int facility, int level,
|
|
|
|
+ const char *dict, size_t dictlen,
|
|
|
|
+ const char *fmt, va_list args)
|
|
|
|
+{
|
|
|
|
+ int printed_len;
|
|
|
|
+ bool in_sched = false;
|
|
|
|
+ unsigned long flags;
|
|
|
|
+
|
|
|
|
+ if (level == LOGLEVEL_SCHED) {
|
|
|
|
+ level = LOGLEVEL_DEFAULT;
|
|
|
|
+ in_sched = true;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ boot_delay_msec(level);
|
|
|
|
+ printk_delay();
|
|
|
|
+
|
|
|
|
+ /* This stops the holder of console_sem just where we want him */
|
|
|
|
+ logbuf_lock_irqsave(flags);
|
|
|
|
+ printed_len = vprintk_store(facility, level, dict, dictlen, fmt, args);
|
|
logbuf_unlock_irqrestore(flags);
|
|
logbuf_unlock_irqrestore(flags);
|
|
|
|
|
|
/* If called from the scheduler, we can not call up(). */
|
|
/* If called from the scheduler, we can not call up(). */
|
|
@@ -2884,16 +2893,20 @@ void wake_up_klogd(void)
|
|
preempt_enable();
|
|
preempt_enable();
|
|
}
|
|
}
|
|
|
|
|
|
-int vprintk_deferred(const char *fmt, va_list args)
|
|
|
|
|
|
+void defer_console_output(void)
|
|
{
|
|
{
|
|
- int r;
|
|
|
|
-
|
|
|
|
- r = vprintk_emit(0, LOGLEVEL_SCHED, NULL, 0, fmt, args);
|
|
|
|
-
|
|
|
|
preempt_disable();
|
|
preempt_disable();
|
|
__this_cpu_or(printk_pending, PRINTK_PENDING_OUTPUT);
|
|
__this_cpu_or(printk_pending, PRINTK_PENDING_OUTPUT);
|
|
irq_work_queue(this_cpu_ptr(&wake_up_klogd_work));
|
|
irq_work_queue(this_cpu_ptr(&wake_up_klogd_work));
|
|
preempt_enable();
|
|
preempt_enable();
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+int vprintk_deferred(const char *fmt, va_list args)
|
|
|
|
+{
|
|
|
|
+ int r;
|
|
|
|
+
|
|
|
|
+ r = vprintk_emit(0, LOGLEVEL_SCHED, NULL, 0, fmt, args);
|
|
|
|
+ defer_console_output();
|
|
|
|
|
|
return r;
|
|
return r;
|
|
}
|
|
}
|