aboutsummaryrefslogtreecommitdiffstats
path: root/xen/arch/x86/hvm/vpt.c
diff options
context:
space:
mode:
authorKeir Fraser <keir@xensource.com>2007-10-26 09:56:54 +0100
committerKeir Fraser <keir@xensource.com>2007-10-26 09:56:54 +0100
commit617d4311ef314ca79bdabe1c1087e42eabba09b8 (patch)
tree32b331607ce6488ee0fea313d831109e7e5d4ebf /xen/arch/x86/hvm/vpt.c
parent5afede5ce640deb26e258c2d2c9dbbecef0fc0a5 (diff)
downloadxen-617d4311ef314ca79bdabe1c1087e42eabba09b8.tar.gz
xen-617d4311ef314ca79bdabe1c1087e42eabba09b8.tar.bz2
xen-617d4311ef314ca79bdabe1c1087e42eabba09b8.zip
hvm, x86: Allow virtual timer mode to be specified.
In HVM config file: timer_mode=0 # Default: virtual time is delayed when timer ticks are # missed dur to preemption timer_mode=1 # Virtual time always equals wall time, even while missed # ticks are pending From: Haitao Shan <haitao.shan@intel.com> Signed-off-by: Keir Fraser <keir@xensource.com>
Diffstat (limited to 'xen/arch/x86/hvm/vpt.c')
-rw-r--r--xen/arch/x86/hvm/vpt.c47
1 files changed, 33 insertions, 14 deletions
diff --git a/xen/arch/x86/hvm/vpt.c b/xen/arch/x86/hvm/vpt.c
index 743f19eaa0..9ce8991594 100644
--- a/xen/arch/x86/hvm/vpt.c
+++ b/xen/arch/x86/hvm/vpt.c
@@ -23,6 +23,12 @@
#include <asm/hvm/vpt.h>
#include <asm/event.h>
+static int pt_support_time_frozen(struct domain *d)
+{
+ return (d->arch.hvm_domain.params[HVM_PARAM_TIMER_MODE] ==
+ HVMPTM_delay_for_missed_ticks);
+}
+
static void pt_lock(struct periodic_time *pt)
{
struct vcpu *v;
@@ -67,7 +73,12 @@ static void missed_ticks(struct periodic_time *pt)
pt->scheduled += missed_ticks * pt->period;
}
-void pt_freeze_time(struct vcpu *v)
+static __inline__ void pt_freeze_time(struct vcpu *v)
+{
+ v->arch.hvm_vcpu.guest_time = hvm_get_guest_time(v);
+}
+
+void pt_save_timer(struct vcpu *v)
{
struct list_head *head = &v->arch.hvm_vcpu.tm_list;
struct periodic_time *pt;
@@ -77,33 +88,40 @@ void pt_freeze_time(struct vcpu *v)
spin_lock(&v->arch.hvm_vcpu.tm_lock);
- v->arch.hvm_vcpu.guest_time = hvm_get_guest_time(v);
-
list_for_each_entry ( pt, head, list )
stop_timer(&pt->timer);
+ if ( pt_support_time_frozen(v->domain) )
+ pt_freeze_time(v);
+
spin_unlock(&v->arch.hvm_vcpu.tm_lock);
}
-void pt_thaw_time(struct vcpu *v)
+static __inline__ void pt_thaw_time(struct vcpu *v)
+{
+ if ( v->arch.hvm_vcpu.guest_time )
+ {
+ hvm_set_guest_time(v, v->arch.hvm_vcpu.guest_time);
+ v->arch.hvm_vcpu.guest_time = 0;
+ }
+}
+
+void pt_restore_timer(struct vcpu *v)
{
struct list_head *head = &v->arch.hvm_vcpu.tm_list;
struct periodic_time *pt;
spin_lock(&v->arch.hvm_vcpu.tm_lock);
- if ( v->arch.hvm_vcpu.guest_time )
+ list_for_each_entry ( pt, head, list )
{
- hvm_set_guest_time(v, v->arch.hvm_vcpu.guest_time);
- v->arch.hvm_vcpu.guest_time = 0;
-
- list_for_each_entry ( pt, head, list )
- {
- missed_ticks(pt);
- set_timer(&pt->timer, pt->scheduled);
- }
+ missed_ticks(pt);
+ set_timer(&pt->timer, pt->scheduled);
}
+ if ( pt_support_time_frozen(v->domain) )
+ pt_thaw_time(v);
+
spin_unlock(&v->arch.hvm_vcpu.tm_lock);
}
@@ -218,7 +236,8 @@ void pt_intr_post(struct vcpu *v, struct hvm_intack intack)
pt->last_plt_gtime += pt->period_cycles;
}
- if ( hvm_get_guest_time(v) < pt->last_plt_gtime )
+ if ( pt_support_time_frozen(v->domain) &&
+ hvm_get_guest_time(v) < pt->last_plt_gtime )
hvm_set_guest_time(v, pt->last_plt_gtime);
cb = pt->cb;