Re: [PATCH] KVM: Factor out kvm_vcpu_kick to arch-generic code

2012-01-23 Thread Marcelo Tosatti
On Thu, Jan 19, 2012 at 10:22:41PM -0500, Christoffer Dall wrote:
> The kvm_vcpu_kick function performs roughly the same funcitonality on
> most all architectures, so we shouldn't have separate copies.
> 
> PowerPC keeps a pointer to interchanging waitqueues on the vcpu_arch
> structure and to accomodate this special need a
> __KVM_HAVE_ARCH_VCPU_GET_WQ define and accompanying function
> kvm_arch_vcpu_wq have been defined. For all other architectures this
> is a generic inline that just returns &vcpu->wq;
> 
> This patch applies to Linus' tree on the Linux 3.3-rc1 tag.
> 
> Signed-off-by: Christoffer Dall 
> ---
>  arch/ia64/include/asm/kvm_host.h|1 +
>  arch/ia64/kvm/kvm-ia64.c|   15 ---
>  arch/powerpc/include/asm/kvm_host.h |6 ++
>  arch/powerpc/kvm/powerpc.c  |   12 ++--
>  arch/x86/kvm/x86.c  |   17 -
>  include/linux/kvm_host.h|8 
>  virt/kvm/kvm_main.c |   23 +++
>  7 files changed, 40 insertions(+), 42 deletions(-)
> 
> diff --git a/arch/ia64/include/asm/kvm_host.h 
> b/arch/ia64/include/asm/kvm_host.h
> index 2689ee5..06a5e91 100644
> --- a/arch/ia64/include/asm/kvm_host.h
> +++ b/arch/ia64/include/asm/kvm_host.h
> @@ -365,6 +365,7 @@ struct thash_cb {
>  };
>  
>  struct kvm_vcpu_stat {
> + u32 halt_wakeup;
>  };
>  
>  struct kvm_vcpu_arch {
> diff --git a/arch/ia64/kvm/kvm-ia64.c b/arch/ia64/kvm/kvm-ia64.c
> index 43f4c92..f22ffb6 100644
> --- a/arch/ia64/kvm/kvm-ia64.c
> +++ b/arch/ia64/kvm/kvm-ia64.c
> @@ -1851,21 +1851,6 @@ void kvm_arch_hardware_unsetup(void)
>  {
>  }
>  
> -void kvm_vcpu_kick(struct kvm_vcpu *vcpu)
> -{
> - int me;
> - int cpu = vcpu->cpu;
> -
> - if (waitqueue_active(&vcpu->wq))
> - wake_up_interruptible(&vcpu->wq);
> -
> - me = get_cpu();
> - if (cpu != me && (unsigned) cpu < nr_cpu_ids && cpu_online(cpu))
> - if (!test_and_set_bit(KVM_REQ_KICK, &vcpu->requests))
> - smp_send_reschedule(cpu);
> - put_cpu();
> -}
> -
>  int kvm_apic_set_irq(struct kvm_vcpu *vcpu, struct kvm_lapic_irq *irq)
>  {
>   return __apic_accept_irq(vcpu, irq->vector);
> diff --git a/arch/powerpc/include/asm/kvm_host.h 
> b/arch/powerpc/include/asm/kvm_host.h
> index bf8af5d..b687444 100644
> --- a/arch/powerpc/include/asm/kvm_host.h
> +++ b/arch/powerpc/include/asm/kvm_host.h
> @@ -438,4 +438,10 @@ struct kvm_vcpu_arch {
>  #define KVMPPC_VCPU_BUSY_IN_HOST 1
>  #define KVMPPC_VCPU_RUNNABLE 2
>  
> +#define __KVM_HAVE_ARCH_VCPU_GET_WQ 1
> +static inline wait_queue_head *kvm_arch_vcpu_wq(struct kvm_vcpu *vcpu)
> +{
> + return vcpu->arch.wqp;
> +}
> +
>  #endif /* __POWERPC_KVM_HOST_H__ */
> diff --git a/arch/powerpc/kvm/powerpc.c b/arch/powerpc/kvm/powerpc.c
> index 607fbdf..30cd621 100644
> --- a/arch/powerpc/kvm/powerpc.c
> +++ b/arch/powerpc/kvm/powerpc.c
> @@ -311,10 +311,7 @@ static void kvmppc_decrementer_func(unsigned long data)
>  
>   kvmppc_core_queue_dec(vcpu);
>  
> - if (waitqueue_active(vcpu->arch.wqp)) {
> - wake_up_interruptible(vcpu->arch.wqp);
> - vcpu->stat.halt_wakeup++;
> - }
> + kvm_vcpu_kick(vcpu);
>  }
>  
>  /*
> @@ -572,12 +569,7 @@ int kvm_vcpu_ioctl_interrupt(struct kvm_vcpu *vcpu, 
> struct kvm_interrupt *irq)
>  
>   kvmppc_core_queue_external(vcpu, irq);
>  
> - if (waitqueue_active(vcpu->arch.wqp)) {
> - wake_up_interruptible(vcpu->arch.wqp);
> - vcpu->stat.halt_wakeup++;
> - } else if (vcpu->cpu != -1) {
> - smp_send_reschedule(vcpu->cpu);
> - }
> + kvm_vcpu_kick(vcpu);
>  
>   return 0;
>  }
> diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
> index c38efd7..6de0af8 100644
> --- a/arch/x86/kvm/x86.c
> +++ b/arch/x86/kvm/x86.c
> @@ -6688,23 +6688,6 @@ int kvm_arch_vcpu_runnable(struct kvm_vcpu *vcpu)
>kvm_cpu_has_interrupt(vcpu));
>  }
>  
> -void kvm_vcpu_kick(struct kvm_vcpu *vcpu)
> -{
> - int me;
> - int cpu = vcpu->cpu;
> -
> - if (waitqueue_active(&vcpu->wq)) {
> - wake_up_interruptible(&vcpu->wq);
> - ++vcpu->stat.halt_wakeup;
> - }
> -
> - me = get_cpu();
> - if (cpu != me && (unsigned)cpu < nr_cpu_ids && cpu_online(cpu))
> - if (kvm_vcpu_exiting_guest_mode(vcpu) == IN_GUEST_MODE)
> - smp_send_reschedule(cpu);
> - put_cpu();
> -}
> -
>  int kvm_arch_interrupt_allowed(struct kvm_vcpu *vcpu)
>  {
>   return kvm_x86_ops->interrupt_allowed(vcpu);
> diff --git a/include/linux/kvm_host.h b/include/linux/kvm_host.h
> index d526231..301ae34 100644
> --- a/include/linux/kvm_host.h
> +++ b/include/linux/kvm_host.h
> @@ -407,6 +407,7 @@ void mark_page_dirty_in_slot(struct kvm *kvm, struct 
> kvm_memory_slot *memslot,
>gfn_t gfn);
>  
>  void kvm_vcpu_block(struct kvm_vcpu *vcpu);
> +void kvm_vcpu_kick(

Re: [PATCH] KVM: Factor out kvm_vcpu_kick to arch-generic code

2012-01-20 Thread Jan Kiszka
On 2012-01-20 04:22, Christoffer Dall wrote:
> diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c
> index d9cfb78..cd30b68 100644
> --- a/virt/kvm/kvm_main.c
> +++ b/virt/kvm/kvm_main.c
> @@ -153,6 +153,7 @@ void vcpu_load(struct kvm_vcpu *vcpu)
>   cpu = get_cpu();
>   preempt_notifier_register(&vcpu->preempt_notifier);
>   kvm_arch_vcpu_load(vcpu, cpu);
> + vcpu->cpu = cpu;

That means setting it in the various kvm_arch_vcpu_load handlers becomes
redundant and should be cleaned up.

Jan

-- 
Siemens AG, Corporate Technology, CT T DE IT 1
Corporate Competence Center Embedded Linux
--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] KVM: Factor out kvm_vcpu_kick to arch-generic code

2012-01-19 Thread Christoffer Dall
The kvm_vcpu_kick function performs roughly the same funcitonality on
most all architectures, so we shouldn't have separate copies.

PowerPC keeps a pointer to interchanging waitqueues on the vcpu_arch
structure and to accomodate this special need a
__KVM_HAVE_ARCH_VCPU_GET_WQ define and accompanying function
kvm_arch_vcpu_wq have been defined. For all other architectures this
is a generic inline that just returns &vcpu->wq;

This patch applies to Linus' tree on the Linux 3.3-rc1 tag.

Signed-off-by: Christoffer Dall 
---
 arch/ia64/include/asm/kvm_host.h|1 +
 arch/ia64/kvm/kvm-ia64.c|   15 ---
 arch/powerpc/include/asm/kvm_host.h |6 ++
 arch/powerpc/kvm/powerpc.c  |   12 ++--
 arch/x86/kvm/x86.c  |   17 -
 include/linux/kvm_host.h|8 
 virt/kvm/kvm_main.c |   23 +++
 7 files changed, 40 insertions(+), 42 deletions(-)

diff --git a/arch/ia64/include/asm/kvm_host.h b/arch/ia64/include/asm/kvm_host.h
index 2689ee5..06a5e91 100644
--- a/arch/ia64/include/asm/kvm_host.h
+++ b/arch/ia64/include/asm/kvm_host.h
@@ -365,6 +365,7 @@ struct thash_cb {
 };
 
 struct kvm_vcpu_stat {
+   u32 halt_wakeup;
 };
 
 struct kvm_vcpu_arch {
diff --git a/arch/ia64/kvm/kvm-ia64.c b/arch/ia64/kvm/kvm-ia64.c
index 43f4c92..f22ffb6 100644
--- a/arch/ia64/kvm/kvm-ia64.c
+++ b/arch/ia64/kvm/kvm-ia64.c
@@ -1851,21 +1851,6 @@ void kvm_arch_hardware_unsetup(void)
 {
 }
 
-void kvm_vcpu_kick(struct kvm_vcpu *vcpu)
-{
-   int me;
-   int cpu = vcpu->cpu;
-
-   if (waitqueue_active(&vcpu->wq))
-   wake_up_interruptible(&vcpu->wq);
-
-   me = get_cpu();
-   if (cpu != me && (unsigned) cpu < nr_cpu_ids && cpu_online(cpu))
-   if (!test_and_set_bit(KVM_REQ_KICK, &vcpu->requests))
-   smp_send_reschedule(cpu);
-   put_cpu();
-}
-
 int kvm_apic_set_irq(struct kvm_vcpu *vcpu, struct kvm_lapic_irq *irq)
 {
return __apic_accept_irq(vcpu, irq->vector);
diff --git a/arch/powerpc/include/asm/kvm_host.h 
b/arch/powerpc/include/asm/kvm_host.h
index bf8af5d..b687444 100644
--- a/arch/powerpc/include/asm/kvm_host.h
+++ b/arch/powerpc/include/asm/kvm_host.h
@@ -438,4 +438,10 @@ struct kvm_vcpu_arch {
 #define KVMPPC_VCPU_BUSY_IN_HOST   1
 #define KVMPPC_VCPU_RUNNABLE   2
 
+#define __KVM_HAVE_ARCH_VCPU_GET_WQ 1
+static inline wait_queue_head *kvm_arch_vcpu_wq(struct kvm_vcpu *vcpu)
+{
+   return vcpu->arch.wqp;
+}
+
 #endif /* __POWERPC_KVM_HOST_H__ */
diff --git a/arch/powerpc/kvm/powerpc.c b/arch/powerpc/kvm/powerpc.c
index 607fbdf..30cd621 100644
--- a/arch/powerpc/kvm/powerpc.c
+++ b/arch/powerpc/kvm/powerpc.c
@@ -311,10 +311,7 @@ static void kvmppc_decrementer_func(unsigned long data)
 
kvmppc_core_queue_dec(vcpu);
 
-   if (waitqueue_active(vcpu->arch.wqp)) {
-   wake_up_interruptible(vcpu->arch.wqp);
-   vcpu->stat.halt_wakeup++;
-   }
+   kvm_vcpu_kick(vcpu);
 }
 
 /*
@@ -572,12 +569,7 @@ int kvm_vcpu_ioctl_interrupt(struct kvm_vcpu *vcpu, struct 
kvm_interrupt *irq)
 
kvmppc_core_queue_external(vcpu, irq);
 
-   if (waitqueue_active(vcpu->arch.wqp)) {
-   wake_up_interruptible(vcpu->arch.wqp);
-   vcpu->stat.halt_wakeup++;
-   } else if (vcpu->cpu != -1) {
-   smp_send_reschedule(vcpu->cpu);
-   }
+   kvm_vcpu_kick(vcpu);
 
return 0;
 }
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index c38efd7..6de0af8 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -6688,23 +6688,6 @@ int kvm_arch_vcpu_runnable(struct kvm_vcpu *vcpu)
 kvm_cpu_has_interrupt(vcpu));
 }
 
-void kvm_vcpu_kick(struct kvm_vcpu *vcpu)
-{
-   int me;
-   int cpu = vcpu->cpu;
-
-   if (waitqueue_active(&vcpu->wq)) {
-   wake_up_interruptible(&vcpu->wq);
-   ++vcpu->stat.halt_wakeup;
-   }
-
-   me = get_cpu();
-   if (cpu != me && (unsigned)cpu < nr_cpu_ids && cpu_online(cpu))
-   if (kvm_vcpu_exiting_guest_mode(vcpu) == IN_GUEST_MODE)
-   smp_send_reschedule(cpu);
-   put_cpu();
-}
-
 int kvm_arch_interrupt_allowed(struct kvm_vcpu *vcpu)
 {
return kvm_x86_ops->interrupt_allowed(vcpu);
diff --git a/include/linux/kvm_host.h b/include/linux/kvm_host.h
index d526231..301ae34 100644
--- a/include/linux/kvm_host.h
+++ b/include/linux/kvm_host.h
@@ -407,6 +407,7 @@ void mark_page_dirty_in_slot(struct kvm *kvm, struct 
kvm_memory_slot *memslot,
 gfn_t gfn);
 
 void kvm_vcpu_block(struct kvm_vcpu *vcpu);
+void kvm_vcpu_kick(struct kvm_vcpu *vcpu);
 void kvm_vcpu_on_spin(struct kvm_vcpu *vcpu);
 void kvm_resched(struct kvm_vcpu *vcpu);
 void kvm_load_guest_fpu(struct kvm_vcpu *vcpu);
@@ -489,6 +490,13 @@ static inline void kvm_arch_free_vm(struct kvm *kvm)
 }
 #endif
 
+#ifndef __KVM_HAVE_ARCH