* [patch 0/2] PIT: optionally disable interrupt reinjection @ 2008-12-29 17:38 Marcelo Tosatti 2008-12-29 17:38 ` [patch 1/2] KVM: PIT: fix i8254 pending count read Marcelo Tosatti 2008-12-29 17:38 ` [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection Marcelo Tosatti 0 siblings, 2 replies; 7+ messages in thread From: Marcelo Tosatti @ 2008-12-29 17:38 UTC (permalink / raw) To: kvm; +Cc: avi, sheng -- ^ permalink raw reply [flat|nested] 7+ messages in thread
* [patch 1/2] KVM: PIT: fix i8254 pending count read 2008-12-29 17:38 [patch 0/2] PIT: optionally disable interrupt reinjection Marcelo Tosatti @ 2008-12-29 17:38 ` Marcelo Tosatti 2008-12-29 17:38 ` [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection Marcelo Tosatti 1 sibling, 0 replies; 7+ messages in thread From: Marcelo Tosatti @ 2008-12-29 17:38 UTC (permalink / raw) To: kvm; +Cc: avi, sheng, Marcelo Tosatti [-- Attachment #1: i8254-fix-count --] [-- Type: text/plain, Size: 669 bytes --] count_load_time assignment is bogus: its supposed to contain what it means, not the expiration time. Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> Index: kvm/arch/x86/kvm/i8254.c =================================================================== --- kvm.orig/arch/x86/kvm/i8254.c +++ kvm/arch/x86/kvm/i8254.c @@ -207,7 +207,7 @@ static int __pit_timer_fn(struct kvm_kpi hrtimer_add_expires_ns(&pt->timer, pt->period); pt->scheduled = hrtimer_get_expires_ns(&pt->timer); if (pt->period) - ps->channels[0].count_load_time = hrtimer_get_expires(&pt->timer); + ps->channels[0].count_load_time = ktime_get(); return (pt->period == 0 ? 0 : 1); } -- ^ permalink raw reply [flat|nested] 7+ messages in thread
* [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection 2008-12-29 17:38 [patch 0/2] PIT: optionally disable interrupt reinjection Marcelo Tosatti 2008-12-29 17:38 ` [patch 1/2] KVM: PIT: fix i8254 pending count read Marcelo Tosatti @ 2008-12-29 17:38 ` Marcelo Tosatti 2008-12-30 10:08 ` Avi Kivity 1 sibling, 1 reply; 7+ messages in thread From: Marcelo Tosatti @ 2008-12-29 17:38 UTC (permalink / raw) To: kvm; +Cc: avi, sheng, Marcelo Tosatti [-- Attachment #1: i8254-disable-reinject --] [-- Type: text/plain, Size: 2576 bytes --] Certain clocks (such as TSC) in older 2.6 guests overaccount for lost ticks, causing severe time drift. Interrupt reinjection magnifies the problem. Provide an option to disable it. Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> Index: kvm/arch/x86/kvm/i8254.c =================================================================== --- kvm.orig/arch/x86/kvm/i8254.c +++ kvm/arch/x86/kvm/i8254.c @@ -201,6 +201,9 @@ static int __pit_timer_fn(struct kvm_kpi if (!atomic_inc_and_test(&pt->pending)) set_bit(KVM_REQ_PENDING_TIMER, &vcpu0->requests); + if (pt->no_reinject) + atomic_set(&pt->pending, 1); + if (vcpu0 && waitqueue_active(&vcpu0->wq)) wake_up_interruptible(&vcpu0->wq); Index: kvm/arch/x86/kvm/i8254.h =================================================================== --- kvm.orig/arch/x86/kvm/i8254.h +++ kvm/arch/x86/kvm/i8254.h @@ -9,6 +9,7 @@ struct kvm_kpit_timer { s64 period; /* unit: ns */ s64 scheduled; atomic_t pending; + bool no_reinject; }; struct kvm_kpit_channel_state { Index: kvm/arch/x86/kvm/x86.c =================================================================== --- kvm.orig/arch/x86/kvm/x86.c +++ kvm/arch/x86/kvm/x86.c @@ -991,6 +991,7 @@ int kvm_dev_ioctl_check_extension(long e case KVM_CAP_NOP_IO_DELAY: case KVM_CAP_MP_STATE: case KVM_CAP_SYNC_MMU: + case KVM_CAP_PIT_NO_REINJECT: r = 1; break; case KVM_CAP_COALESCED_MMIO: @@ -1723,6 +1724,12 @@ static int kvm_vm_ioctl_set_pit(struct k return r; } +static int kvm_vm_ioctl_no_reinject(struct kvm *kvm) +{ + kvm->arch.vpit->pit_state.pit_timer.no_reinject = true; + return 0; +} + /* * Get (and clear) the dirty memory log for a memory slot. */ @@ -1920,6 +1927,16 @@ long kvm_arch_vm_ioctl(struct file *filp r = 0; break; } + case KVM_PIT_NO_REINJECT: { + r = -ENXIO; + if (!kvm->arch.vpit) + goto out; + r = kvm_vm_ioctl_no_reinject(kvm); + if (r) + goto out; + r = 0; + break; + } default: ; } Index: kvm/include/linux/kvm.h =================================================================== --- kvm.orig/include/linux/kvm.h +++ kvm/include/linux/kvm.h @@ -396,6 +396,9 @@ struct kvm_trace_rec { #if defined(CONFIG_X86) #define KVM_CAP_SET_GUEST_DEBUG 23 #endif +#if defined(CONFIG_X86) +#define KVM_CAP_PIT_NO_REINJECT 24 +#endif /* * ioctls for VM fds @@ -429,6 +432,7 @@ struct kvm_trace_rec { struct kvm_assigned_pci_dev) #define KVM_ASSIGN_IRQ _IOR(KVMIO, 0x70, \ struct kvm_assigned_irq) +#define KVM_PIT_NO_REINJECT _IO(KVMIO, 0x71) /* * ioctls for vcpu fds -- ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection 2008-12-29 17:38 ` [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection Marcelo Tosatti @ 2008-12-30 10:08 ` Avi Kivity 2008-12-30 16:13 ` Marcelo Tosatti 0 siblings, 1 reply; 7+ messages in thread From: Avi Kivity @ 2008-12-30 10:08 UTC (permalink / raw) To: Marcelo Tosatti; +Cc: kvm, sheng Marcelo Tosatti wrote: > Certain clocks (such as TSC) in older 2.6 guests overaccount for lost > ticks, causing severe time drift. Interrupt reinjection magnifies the > problem. > > Provide an option to disable it. > > Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> > > Index: kvm/arch/x86/kvm/i8254.c > =================================================================== > --- kvm.orig/arch/x86/kvm/i8254.c > +++ kvm/arch/x86/kvm/i8254.c > @@ -201,6 +201,9 @@ static int __pit_timer_fn(struct kvm_kpi > if (!atomic_inc_and_test(&pt->pending)) > set_bit(KVM_REQ_PENDING_TIMER, &vcpu0->requests); > > + if (pt->no_reinject) > + atomic_set(&pt->pending, 1); > + > What about moving this to the place where we atomic_inc()? Any reason not to? > --- kvm.orig/arch/x86/kvm/i8254.h > +++ kvm/arch/x86/kvm/i8254.h > @@ -9,6 +9,7 @@ struct kvm_kpit_timer { > s64 period; /* unit: ns */ > s64 scheduled; > atomic_t pending; > + bool no_reinject; > }; > Negative logic = !good. Call it reinject and init to true. > @@ -991,6 +991,7 @@ int kvm_dev_ioctl_check_extension(long e > case KVM_CAP_NOP_IO_DELAY: > case KVM_CAP_MP_STATE: > case KVM_CAP_SYNC_MMU: > + case KVM_CAP_PIT_NO_REINJECT: > Negative logic. PIT_REINJECT_CONTROL? -- error compiling committee.c: too many arguments to function ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection 2008-12-30 10:08 ` Avi Kivity @ 2008-12-30 16:13 ` Marcelo Tosatti 2008-12-30 16:35 ` Avi Kivity 0 siblings, 1 reply; 7+ messages in thread From: Marcelo Tosatti @ 2008-12-30 16:13 UTC (permalink / raw) To: Avi Kivity; +Cc: kvm, sheng On Tue, Dec 30, 2008 at 12:08:01PM +0200, Avi Kivity wrote: > Marcelo Tosatti wrote: >> Certain clocks (such as TSC) in older 2.6 guests overaccount for lost >> ticks, causing severe time drift. Interrupt reinjection magnifies the >> problem. >> >> Provide an option to disable it. >> >> Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> >> >> Index: kvm/arch/x86/kvm/i8254.c >> =================================================================== >> --- kvm.orig/arch/x86/kvm/i8254.c >> +++ kvm/arch/x86/kvm/i8254.c >> @@ -201,6 +201,9 @@ static int __pit_timer_fn(struct kvm_kpi >> if (!atomic_inc_and_test(&pt->pending)) >> set_bit(KVM_REQ_PENDING_TIMER, &vcpu0->requests); >> + if (pt->no_reinject) >> + atomic_set(&pt->pending, 1); >> + >> > > What about moving this to the place where we atomic_inc()? Any reason > not to? The atomic_inc_and_test is right above, and we want to set KVM_REQ_PENDING_TIMER on 0->1 transitions, so better keep it separate. BTW the KVM_REQ_PENDING_TIMER optimization is broken (atomic_inc_and_test returns true if the _new_ value is zero) but thats another issue. Can't see the improvement you're suggesting. >> --- kvm.orig/arch/x86/kvm/i8254.h >> +++ kvm/arch/x86/kvm/i8254.h >> @@ -9,6 +9,7 @@ struct kvm_kpit_timer { >> s64 period; /* unit: ns */ >> s64 scheduled; >> atomic_t pending; >> + bool no_reinject; >> }; >> > > Negative logic = !good. Call it reinject and init to true. Sure. ^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection 2008-12-30 16:13 ` Marcelo Tosatti @ 2008-12-30 16:35 ` Avi Kivity 0 siblings, 0 replies; 7+ messages in thread From: Avi Kivity @ 2008-12-30 16:35 UTC (permalink / raw) To: Marcelo Tosatti; +Cc: kvm, sheng Marcelo Tosatti wrote: > On Tue, Dec 30, 2008 at 12:08:01PM +0200, Avi Kivity wrote: > >> Marcelo Tosatti wrote: >> >>> Certain clocks (such as TSC) in older 2.6 guests overaccount for lost >>> ticks, causing severe time drift. Interrupt reinjection magnifies the >>> problem. >>> >>> Provide an option to disable it. >>> >>> Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> >>> >>> Index: kvm/arch/x86/kvm/i8254.c >>> =================================================================== >>> --- kvm.orig/arch/x86/kvm/i8254.c >>> +++ kvm/arch/x86/kvm/i8254.c >>> @@ -201,6 +201,9 @@ static int __pit_timer_fn(struct kvm_kpi >>> if (!atomic_inc_and_test(&pt->pending)) >>> set_bit(KVM_REQ_PENDING_TIMER, &vcpu0->requests); >>> + if (pt->no_reinject) >>> + atomic_set(&pt->pending, 1); >>> + >>> >>> >> What about moving this to the place where we atomic_inc()? Any reason >> not to? >> > > The atomic_inc_and_test is right above, and we want to set > KVM_REQ_PENDING_TIMER on 0->1 transitions, so better keep it > separate. BTW the KVM_REQ_PENDING_TIMER optimization is broken > (atomic_inc_and_test returns true if the _new_ value is zero) but thats > another issue. > > Can't see the improvement you're suggesting. > Right, scratch that. Didn't read closely enough. -- error compiling committee.c: too many arguments to function ^ permalink raw reply [flat|nested] 7+ messages in thread
* [patch 0/2] PIT: optionally disable interrupt reinjection (v2) @ 2008-12-30 17:55 Marcelo Tosatti 2008-12-30 17:55 ` [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection Marcelo Tosatti 0 siblings, 1 reply; 7+ messages in thread From: Marcelo Tosatti @ 2008-12-30 17:55 UTC (permalink / raw) To: kvm; +Cc: avi, sheng Addressing comments. -- ^ permalink raw reply [flat|nested] 7+ messages in thread
* [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection 2008-12-30 17:55 [patch 0/2] PIT: optionally disable interrupt reinjection (v2) Marcelo Tosatti @ 2008-12-30 17:55 ` Marcelo Tosatti 0 siblings, 0 replies; 7+ messages in thread From: Marcelo Tosatti @ 2008-12-30 17:55 UTC (permalink / raw) To: kvm; +Cc: avi, sheng, Marcelo Tosatti [-- Attachment #1: i8254-disable-reinject --] [-- Type: text/plain, Size: 3516 bytes --] Certain clocks (such as TSC) in older 2.6 guests overaccount for lost ticks, causing severe time drift. Interrupt reinjection magnifies the problem. Provide an option to disable it. Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> Index: kvm/arch/x86/kvm/i8254.c =================================================================== --- kvm.orig/arch/x86/kvm/i8254.c +++ kvm/arch/x86/kvm/i8254.c @@ -201,6 +201,9 @@ static int __pit_timer_fn(struct kvm_kpi if (!atomic_inc_and_test(&pt->pending)) set_bit(KVM_REQ_PENDING_TIMER, &vcpu0->requests); + if (!pt->reinject) + atomic_set(&pt->pending, 1); + if (vcpu0 && waitqueue_active(&vcpu0->wq)) wake_up_interruptible(&vcpu0->wq); @@ -580,6 +583,7 @@ struct kvm_pit *kvm_create_pit(struct kv pit_state->irq_ack_notifier.gsi = 0; pit_state->irq_ack_notifier.irq_acked = kvm_pit_ack_irq; kvm_register_irq_ack_notifier(kvm, &pit_state->irq_ack_notifier); + pit_state->pit_timer.reinject = true; mutex_unlock(&pit->pit_state.lock); kvm_pit_reset(pit); Index: kvm/arch/x86/kvm/i8254.h =================================================================== --- kvm.orig/arch/x86/kvm/i8254.h +++ kvm/arch/x86/kvm/i8254.h @@ -9,6 +9,7 @@ struct kvm_kpit_timer { s64 period; /* unit: ns */ s64 scheduled; atomic_t pending; + bool reinject; }; struct kvm_kpit_channel_state { Index: kvm/arch/x86/kvm/x86.c =================================================================== --- kvm.orig/arch/x86/kvm/x86.c +++ kvm/arch/x86/kvm/x86.c @@ -991,6 +991,7 @@ int kvm_dev_ioctl_check_extension(long e case KVM_CAP_NOP_IO_DELAY: case KVM_CAP_MP_STATE: case KVM_CAP_SYNC_MMU: + case KVM_CAP_PIT_REINJECT_CONTROL: r = 1; break; case KVM_CAP_COALESCED_MMIO: @@ -1723,6 +1724,13 @@ static int kvm_vm_ioctl_set_pit(struct k return r; } +static int kvm_vm_ioctl_pit_reinject(struct kvm *kvm, + struct kvm_pit_reinject_control *control) +{ + kvm->arch.vpit->pit_state.pit_timer.reinject = control->reinject; + return 0; +} + /* * Get (and clear) the dirty memory log for a memory slot. */ @@ -1920,6 +1928,20 @@ long kvm_arch_vm_ioctl(struct file *filp r = 0; break; } + case KVM_PIT_REINJECT_CONTROL: { + struct kvm_pit_reinject_control control; + r = -EFAULT; + if (copy_from_user(&control, argp, sizeof(control))) + goto out; + r = -ENXIO; + if (!kvm->arch.vpit) + goto out; + r = kvm_vm_ioctl_pit_reinject(kvm, &control); + if (r) + goto out; + r = 0; + break; + } default: ; } Index: kvm/include/linux/kvm.h =================================================================== --- kvm.orig/include/linux/kvm.h +++ kvm/include/linux/kvm.h @@ -396,6 +396,9 @@ struct kvm_trace_rec { #if defined(CONFIG_X86) #define KVM_CAP_SET_GUEST_DEBUG 23 #endif +#if defined(CONFIG_X86) +#define KVM_CAP_PIT_REINJECT_CONTROL 24 +#endif /* * ioctls for VM fds @@ -429,6 +432,7 @@ struct kvm_trace_rec { struct kvm_assigned_pci_dev) #define KVM_ASSIGN_IRQ _IOR(KVMIO, 0x70, \ struct kvm_assigned_irq) +#define KVM_PIT_REINJECT_CONTROL _IO(KVMIO, 0x71) /* * ioctls for vcpu fds Index: kvm/arch/x86/include/asm/kvm.h =================================================================== --- kvm.orig/arch/x86/include/asm/kvm.h +++ kvm/arch/x86/include/asm/kvm.h @@ -226,4 +226,8 @@ struct kvm_guest_debug_arch { struct kvm_pit_state { struct kvm_pit_channel_state channels[3]; }; + +struct kvm_pit_reinject_control { + __u8 reinject; +}; #endif /* _ASM_X86_KVM_H */ -- ^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2008-12-30 18:02 UTC | newest] Thread overview: 7+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2008-12-29 17:38 [patch 0/2] PIT: optionally disable interrupt reinjection Marcelo Tosatti 2008-12-29 17:38 ` [patch 1/2] KVM: PIT: fix i8254 pending count read Marcelo Tosatti 2008-12-29 17:38 ` [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection Marcelo Tosatti 2008-12-30 10:08 ` Avi Kivity 2008-12-30 16:13 ` Marcelo Tosatti 2008-12-30 16:35 ` Avi Kivity -- strict thread matches above, loose matches on Subject: below -- 2008-12-30 17:55 [patch 0/2] PIT: optionally disable interrupt reinjection (v2) Marcelo Tosatti 2008-12-30 17:55 ` [patch 2/2] KVM: PIT: provide an option to disable interrupt reinjection Marcelo Tosatti
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox