Commit 1aaad49e856ce41adc07d8ae0c8ef35fc4483245

Authored by Frans Pop
Committed by Ingo Molnar
1 parent 8259cf4342

printk: Restore previous console_loglevel when re-enabling logging

When logging to console is disabled from userspace using klogctl()
and later re-enabled, console_loglevel gets set to the default
log level instead to the previous value.

This means that if the kernel was booted with 'quiet', the boot is
suddenly no longer quiet after logging to console gets re-enabled.

Save the current console_loglevel when logging is disabled and
restore to that value. If the log level is set to a specific value
while disabled, this is interpreted as an implicit re-enabling of
the logging.

The problem that prompted this patch is described in:

    http://lkml.org/lkml/2009/6/28/234

There are two variations possible on the patch below:

 1) If klogctl(7) is called while logging is not disabled, then set level
    to default (partially preserving current functionality):
  	case 7:		/* Enable logging to console */
 -		console_loglevel = default_console_loglevel;
 +		if (saved_console_loglevel == -1)
 +			console_loglevel = default_console_loglevel;
 +		else {
 +			console_loglevel = saved_console_loglevel;
 +			saved_console_loglevel = -1;
 +		}

 2) If klogctl(8) is called while logging is disabled, then don't enable
    logging, but remember the requested value for when logging does get
    enabled again:
  	case 8:		/* Set level of messages printed to console */
 [...]
 - 		console_loglevel = len;
 +		if (saved_console_loglevel == -1)
 +			console_loglevel = len;
 +		else
 +			saved_console_loglevel = len;

Yet another option would be to ignore the request.

Signed-off-by: Frans Pop <elendil@planet.nl>
Cc: cryptsetup@packages.debian.org
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Linus Torvalds <torvalds@linux-foundation.org>
LKML-Reference: <200907061331.49930.elendil@planet.nl>
Signed-off-by: Ingo Molnar <mingo@elte.hu>

Showing 1 changed file with 10 additions and 1 deletions Side-by-side Diff

... ... @@ -67,6 +67,8 @@
67 67 DEFAULT_CONSOLE_LOGLEVEL, /* default_console_loglevel */
68 68 };
69 69  
  70 +static int saved_console_loglevel = -1;
  71 +
70 72 /*
71 73 * Low level drivers may need that to know if they can schedule in
72 74 * their unblank() callback or not. So let's export it.
73 75  
... ... @@ -378,10 +380,15 @@
378 380 logged_chars = 0;
379 381 break;
380 382 case 6: /* Disable logging to console */
  383 + if (saved_console_loglevel == -1)
  384 + saved_console_loglevel = console_loglevel;
381 385 console_loglevel = minimum_console_loglevel;
382 386 break;
383 387 case 7: /* Enable logging to console */
384   - console_loglevel = default_console_loglevel;
  388 + if (saved_console_loglevel != -1) {
  389 + console_loglevel = saved_console_loglevel;
  390 + saved_console_loglevel = -1;
  391 + }
385 392 break;
386 393 case 8: /* Set level of messages printed to console */
387 394 error = -EINVAL;
... ... @@ -390,6 +397,8 @@
390 397 if (len < minimum_console_loglevel)
391 398 len = minimum_console_loglevel;
392 399 console_loglevel = len;
  400 + /* Implicitly re-enable logging to console */
  401 + saved_console_loglevel = -1;
393 402 error = 0;
394 403 break;
395 404 case 9: /* Number of chars in the log buffer */