提交 600bca59 编写于 作者: P Peter Krempa

qemu: hyperv: Add support for timer enlightenments

Add a new <timer> for the HyperV reference time counter enlightenment
and the iTSC reference page for Windows guests.

This feature provides a paravirtual approach to track timer events for
the guest (similar to kvmclock) with the option to use real hardware
clock on systems with a iTSC with compensation across various hosts.
上级 8ffaa42d
......@@ -1367,7 +1367,13 @@
being modified, and can be one of
"platform" (currently unsupported),
"hpet" (libxl, xen, qemu), "kvmclock" (qemu),
"pit" (qemu), "rtc" (qemu), or "tsc" (libxl).
"pit" (qemu), "rtc" (qemu), "tsc" (libxl) or "hypervclock"
(qemu - <span class="since">since 1.2.2</span>).
The <code>hypervclock</code> timer adds support for the
reference time counter and the reference page for iTSC
feature for guests running the Microsoft Windows
operating system.
</dd>
<dt><code>track</code></dt>
<dd>
......
......@@ -915,7 +915,10 @@
</group>
<group>
<attribute name="name">
<value>kvmclock</value>
<choice>
<value>kvmclock</value>
<value>hypervclock</value>
</choice>
</attribute>
</group>
</choice>
......
......@@ -726,7 +726,8 @@ VIR_ENUM_IMPL(virDomainTimerName, VIR_DOMAIN_TIMER_NAME_LAST,
"rtc",
"hpet",
"tsc",
"kvmclock");
"kvmclock",
"hypervclock");
VIR_ENUM_IMPL(virDomainTimerTrack, VIR_DOMAIN_TIMER_TRACK_LAST,
"boot",
......@@ -2929,7 +2930,8 @@ virDomainDefPostParseInternal(virDomainDefPtr def,
for (i = 0; i < def->clock.ntimers; i++) {
virDomainTimerDefPtr timer = def->clock.timers[i];
if (timer->name == VIR_DOMAIN_TIMER_NAME_KVMCLOCK) {
if (timer->name == VIR_DOMAIN_TIMER_NAME_KVMCLOCK ||
timer->name == VIR_DOMAIN_TIMER_NAME_HYPERVCLOCK) {
if (timer->tickpolicy != -1) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
_("timer %s doesn't support setting of "
......
......@@ -1750,6 +1750,7 @@ enum virDomainTimerNameType {
VIR_DOMAIN_TIMER_NAME_HPET,
VIR_DOMAIN_TIMER_NAME_TSC,
VIR_DOMAIN_TIMER_NAME_KVMCLOCK,
VIR_DOMAIN_TIMER_NAME_HYPERVCLOCK,
VIR_DOMAIN_TIMER_NAME_LAST
};
......
......@@ -6732,20 +6732,23 @@ qemuBuildCpuArgStr(virQEMUDriverPtr driver,
}
}
/* Now force kvmclock on/off based on the corresponding <timer> element. */
/* Handle paravirtual timers */
for (i = 0; i < def->clock.ntimers; i++) {
if (def->clock.timers[i]->name == VIR_DOMAIN_TIMER_NAME_KVMCLOCK &&
def->clock.timers[i]->present != -1) {
char sign;
if (def->clock.timers[i]->present)
sign = '+';
else
sign = '-';
virDomainTimerDefPtr timer = def->clock.timers[i];
if (timer->present == -1)
continue;
if (timer->name == VIR_DOMAIN_TIMER_NAME_KVMCLOCK) {
virBufferAsprintf(&buf, "%s,%ckvmclock",
have_cpu ? "" : default_model,
sign);
timer->present ? '+' : '-');
have_cpu = true;
} else if (timer->name == VIR_DOMAIN_TIMER_NAME_HYPERVCLOCK &&
timer->present) {
virBufferAsprintf(&buf, "%s,hv_time",
have_cpu ? "" : default_model);
have_cpu = true;
break;
}
}
......@@ -8007,8 +8010,7 @@ qemuBuildCommandLine(virConnectPtr conn,
}
for (i = 0; i < def->clock.ntimers; i++) {
switch (def->clock.timers[i]->name) {
default:
switch ((enum virDomainTimerNameType) def->clock.timers[i]->name) {
case VIR_DOMAIN_TIMER_NAME_PLATFORM:
case VIR_DOMAIN_TIMER_NAME_TSC:
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
......@@ -8017,7 +8019,9 @@ qemuBuildCommandLine(virConnectPtr conn,
goto error;
case VIR_DOMAIN_TIMER_NAME_KVMCLOCK:
/* This is handled when building -cpu. */
case VIR_DOMAIN_TIMER_NAME_HYPERVCLOCK:
/* Timers above are handled when building -cpu. */
case VIR_DOMAIN_TIMER_NAME_LAST:
break;
case VIR_DOMAIN_TIMER_NAME_RTC:
......
LC_ALL=C PATH=/bin HOME=/home/test USER=test LOGNAME=test QEMU_AUDIO_DRV=none \
/usr/bin/kvm -S -M pc \
-cpu qemu32,hv_time -m 214 -smp 6 \
-nographic -monitor unix:/tmp/test-monitor,server,nowait -no-acpi -boot n -usb -net \
none -serial none -parallel none
<domain type='kvm'>
<name>QEMUGuest1</name>
<uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
<memory unit='KiB'>219100</memory>
<currentMemory unit='KiB'>219100</currentMemory>
<vcpu placement='static'>6</vcpu>
<os>
<type arch='i686' machine='pc'>hvm</type>
<boot dev='network'/>
</os>
<features>
<pae/>
</features>
<clock offset='utc'>
<timer name='hypervclock' present='yes'/>
</clock>
<on_poweroff>destroy</on_poweroff>
<on_reboot>restart</on_reboot>
<on_crash>destroy</on_crash>
<devices>
<emulator>/usr/bin/kvm</emulator>
<controller type='usb' index='0'/>
<controller type='pci' index='0' model='pci-root'/>
<memballoon model='virtio'/>
</devices>
</domain>
......@@ -637,6 +637,7 @@ mymain(void)
DO_TEST("cpu-kvmclock", QEMU_CAPS_ENABLE_KVM);
DO_TEST("cpu-host-kvmclock", QEMU_CAPS_ENABLE_KVM, QEMU_CAPS_CPU_HOST);
DO_TEST("kvmclock", QEMU_CAPS_KVM);
DO_TEST("clock-timer-hyperv-rtc", QEMU_CAPS_KVM);
DO_TEST("cpu-eoi-disabled", QEMU_CAPS_ENABLE_KVM);
DO_TEST("cpu-eoi-enabled", QEMU_CAPS_ENABLE_KVM);
......
......@@ -160,6 +160,7 @@ mymain(void)
DO_TEST("cpu-host-kvmclock");
DO_TEST("clock-catchup");
DO_TEST("kvmclock");
DO_TEST("clock-timer-hyperv-rtc");
DO_TEST("cpu-eoi-disabled");
DO_TEST("cpu-eoi-enabled");
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册