• Petr Mladek's avatar
    kdb: call vkdb_printf() from vprintk_default() only when wanted · 34aaff40
    Petr Mladek authored
    kdb_trap_printk allows to pass normal printk() messages to kdb via
    vkdb_printk().  For example, it is used to get backtrace using the
    classic show_stack(), see kdb_show_stack().
    
    vkdb_printf() tries to avoid a potential infinite loop by disabling the
    trap.  But this approach is racy, for example:
    
    CPU1					CPU2
    
    vkdb_printf()
      // assume that kdb_trap_printk == 0
      saved_trap_printk = kdb_trap_printk;
      kdb_trap_printk = 0;
    
    					kdb_show_stack()
    					  kdb_trap_printk++;
    
    Problem1: Now, a nested printk() on CPU0 calls vkdb_printf()
    	  even when it should have been disabled. It will not
    	  cause a deadlock but...
    
       // using the outdated saved value: 0
       kdb_trap_printk = saved_trap_printk;
    
    					  kdb_trap_printk--;
    
    Problem2: Now, kdb_trap_printk == -1 and will stay like this.
       It means that all messages will get passed to kdb from
       now on.
    
    This patch removes the racy saved_trap_printk handling.  Instead, the
    recursion is prevented b...
    34aaff40
printk.c 84 KB