• Paul E. McKenney's avatar
    srcu: Create an srcu_read_lock_nmisafe() and srcu_read_unlock_nmisafe() · 2e83b879
    Paul E. McKenney authored
    On strict load-store architectures, the use of this_cpu_inc() by
    srcu_read_lock() and srcu_read_unlock() is not NMI-safe in TREE SRCU.
    To see this suppose that an NMI arrives in the middle of srcu_read_lock(),
    just after it has read ->srcu_lock_count, but before it has written
    the incremented value back to memory.  If that NMI handler also does
    srcu_read_lock() and srcu_read_lock() on that same srcu_struct structure,
    then upon return from that NMI handler, the interrupted srcu_read_lock()
    will overwrite the NMI handler's update to ->srcu_lock_count, but
    leave unchanged the NMI handler's update by srcu_read_unlock() to
    ->srcu_unlock_count.
    
    This can result in a too-short SRCU grace period, which can in turn
    result in arbitrary memory corruption.
    
    If the NMI handler instead interrupts the srcu_read_unlock(), this
    can result in eternal SRCU grace periods, which is not much better.
    
    This commit therefore creates a pair of new srcu_read_lock_nmisafe()
    and srcu_read_unlock_nmisafe() functions, which allow SRCU readers in
    both NMI handlers and in process and IRQ context.  It is bad practice
    to mix the existing and the new _nmisafe() primitives on the same
    srcu_struct structure.  Use one set or the other, not both.
    
    Just to underline that "bad practice" point, using srcu_read_lock() at
    process level and srcu_read_lock_nmisafe() in your NMI handler will not,
    repeat NOT, work.  If you do not immediately understand why this is the
    case, please review the earlier paragraphs in this commit log.
    
    [ paulmck: Apply kernel test robot feedback. ]
    [ paulmck: Apply feedback from Randy Dunlap. ]
    [ paulmck: Apply feedback from John Ogness. ]
    [ paulmck: Apply feedback from Frederic Weisbecker. ]
    
    Link: https://lore.kernel.org/all/20220910221947.171557773@linutronix.de/Signed-off-by: default avatarPaul E. McKenney <paulmck@kernel.org>
    Acked-by: Randy Dunlap <rdunlap@infradead.org> # build-tested
    Reviewed-by: default avatarFrederic Weisbecker <frederic@kernel.org>
    Cc: Thomas Gleixner <tglx@linutronix.de>
    Cc: John Ogness <john.ogness@linutronix.de>
    Cc: Petr Mladek <pmladek@suse.com>
    2e83b879
Kconfig 42.4 KB