• Boqun Feng's avatar
    kvm/x86: Avoid async PF preempting the kernel incorrectly · a2b7861b
    Boqun Feng authored
    Currently, in PREEMPT_COUNT=n kernel, kvm_async_pf_task_wait() could call
    schedule() to reschedule in some cases.  This could result in
    accidentally ending the current RCU read-side critical section early,
    causing random memory corruption in the guest, or otherwise preempting
    the currently running task inside between preempt_disable and
    preempt_enable.
    
    The difficulty to handle this well is because we don't know whether an
    async PF delivered in a preemptible section or RCU read-side critical section
    for PREEMPT_COUNT=n, since preempt_disable()/enable() and rcu_read_lock/unlock()
    are both no-ops in that case.
    
    To cure this, we treat any async PF interrupting a kernel context as one
    that cannot be preempted, preventing kvm_async_pf_task_wait() from choosing
    the schedule() path in that case.
    
    To do so, a second parameter for kvm_async_pf_task_wait() is introduced,
    so that we know whether it's called from a context interrupting the
    kernel, and the parameter is set properly in all the callsites.
    
    Cc: "Paul E. McKenney" <paulmck@linux.vnet.ibm.com>
    Cc: Peter Zijlstra <peterz@infradead.org>
    Cc: Wanpeng Li <wanpeng.li@hotmail.com>
    Cc: stable@vger.kernel.org
    Signed-off-by: default avatarBoqun Feng <boqun.feng@gmail.com>
    Signed-off-by: default avatarRadim Krčmář <rkrcmar@redhat.com>
    a2b7861b
kvm.c 15 KB