diff options
Diffstat (limited to 'kernel')
-rw-r--r-- | kernel/printk.c | 23 |
1 files changed, 21 insertions, 2 deletions
diff --git a/kernel/printk.c b/kernel/printk.c index 6c3d5bf14da2..a41106e19077 100644 --- a/kernel/printk.c +++ b/kernel/printk.c | |||
@@ -361,6 +361,7 @@ static void log_store(int facility, int level, | |||
361 | struct devkmsg_user { | 361 | struct devkmsg_user { |
362 | u64 seq; | 362 | u64 seq; |
363 | u32 idx; | 363 | u32 idx; |
364 | enum log_flags prev; | ||
364 | struct mutex lock; | 365 | struct mutex lock; |
365 | char buf[8192]; | 366 | char buf[8192]; |
366 | }; | 367 | }; |
@@ -426,6 +427,7 @@ static ssize_t devkmsg_read(struct file *file, char __user *buf, | |||
426 | struct log *msg; | 427 | struct log *msg; |
427 | u64 ts_usec; | 428 | u64 ts_usec; |
428 | size_t i; | 429 | size_t i; |
430 | char cont = '-'; | ||
429 | size_t len; | 431 | size_t len; |
430 | ssize_t ret; | 432 | ssize_t ret; |
431 | 433 | ||
@@ -463,8 +465,25 @@ static ssize_t devkmsg_read(struct file *file, char __user *buf, | |||
463 | msg = log_from_idx(user->idx); | 465 | msg = log_from_idx(user->idx); |
464 | ts_usec = msg->ts_nsec; | 466 | ts_usec = msg->ts_nsec; |
465 | do_div(ts_usec, 1000); | 467 | do_div(ts_usec, 1000); |
466 | len = sprintf(user->buf, "%u,%llu,%llu;", | 468 | |
467 | (msg->facility << 3) | msg->level, user->seq, ts_usec); | 469 | /* |
470 | * If we couldn't merge continuation line fragments during the print, | ||
471 | * export the stored flags to allow an optional external merge of the | ||
472 | * records. Merging the records isn't always neccessarily correct, like | ||
473 | * when we hit a race during printing. In most cases though, it produces | ||
474 | * better readable output. 'c' in the record flags mark the first | ||
475 | * fragment of a line, '+' the following. | ||
476 | */ | ||
477 | if (msg->flags & LOG_CONT && !(user->prev & LOG_CONT)) | ||
478 | cont = 'c'; | ||
479 | else if ((msg->flags & LOG_CONT) || | ||
480 | ((user->prev & LOG_CONT) && !(msg->flags & LOG_PREFIX))) | ||
481 | cont = '+'; | ||
482 | |||
483 | len = sprintf(user->buf, "%u,%llu,%llu,%c;", | ||
484 | (msg->facility << 3) | msg->level, | ||
485 | user->seq, ts_usec, cont); | ||
486 | user->prev = msg->flags; | ||
468 | 487 | ||
469 | /* escape non-printable characters */ | 488 | /* escape non-printable characters */ |
470 | for (i = 0; i < msg->text_len; i++) { | 489 | for (i = 0; i < msg->text_len; i++) { |