Every time userspace calls KVM_RUM, we check if another thread started running the VCPU, and in that case, we adjust the vcpu->pid field to the new thread. We obviously only want to perform this logic once we hold the vcpu->mutex and are actually going to run the VCPU. As we are about to move the vcpu_load() call into the architecture-specific implementation of the ioctl, we first factor the pid adjustment logic out in its own function which each architecture can call later on. Signed-off-by: Christoffer Dall <christoffer.dall@xxxxxxxxxx> --- include/linux/kvm_host.h | 2 ++ virt/kvm/kvm_main.c | 28 +++++++++++++++++----------- 2 files changed, 19 insertions(+), 11 deletions(-) diff --git a/include/linux/kvm_host.h b/include/linux/kvm_host.h index 6882538eda32..739a2f8e74c5 100644 --- a/include/linux/kvm_host.h +++ b/include/linux/kvm_host.h @@ -536,6 +536,8 @@ void kvm_vcpu_uninit(struct kvm_vcpu *vcpu); int __must_check vcpu_load(struct kvm_vcpu *vcpu); void vcpu_put(struct kvm_vcpu *vcpu); +void kvm_vcpu_run_adjust_pid(struct kvm_vcpu *vcpu); + #ifdef __KVM_HAVE_IOAPIC void kvm_arch_post_irq_ack_notifier_list_update(struct kvm *kvm); void kvm_arch_post_irq_routing_update(struct kvm *kvm); diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index fafafcc38b5a..c9549d44c489 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -2504,6 +2504,22 @@ static int kvm_vcpu_ioctl_set_sigmask(struct kvm_vcpu *vcpu, sigset_t *sigset) return 0; } +void kvm_vcpu_run_adjust_pid(struct kvm_vcpu *vcpu) +{ + struct pid *oldpid; + + oldpid = rcu_access_pointer(vcpu->pid); + if (unlikely(oldpid != current->pids[PIDTYPE_PID].pid)) { + /* The thread running this VCPU changed. */ + struct pid *newpid = get_task_pid(current, PIDTYPE_PID); + + rcu_assign_pointer(vcpu->pid, newpid); + if (oldpid) + synchronize_rcu(); + put_pid(oldpid); + } +} + static long kvm_vcpu_ioctl(struct file *filp, unsigned int ioctl, unsigned long arg) { @@ -2530,23 +2546,13 @@ static long kvm_vcpu_ioctl(struct file *filp, switch (ioctl) { case KVM_RUN: { - struct pid *oldpid; r = -EINVAL; if (arg) goto out; r = vcpu_load(vcpu); if (r) goto out; - oldpid = rcu_access_pointer(vcpu->pid); - if (unlikely(oldpid != current->pids[PIDTYPE_PID].pid)) { - /* The thread running this VCPU changed. */ - struct pid *newpid = get_task_pid(current, PIDTYPE_PID); - - rcu_assign_pointer(vcpu->pid, newpid); - if (oldpid) - synchronize_rcu(); - put_pid(oldpid); - } + kvm_vcpu_run_adjust_pid(vcpu); r = kvm_arch_vcpu_ioctl_run(vcpu, vcpu->run); vcpu_put(vcpu); trace_kvm_userspace_exit(vcpu->run->exit_reason, r); -- 2.14.2 -- To unsubscribe from this list: send the line "unsubscribe linux-s390" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html