mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-02-01 17:35:17 +00:00
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.
This commit is contained in:
parent
8ffaa42d7b
commit
600bca592b
@ -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:
|
||||
|
@ -0,0 +1,5 @@
|
||||
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
|
@ -0,0 +1,26 @@
|
||||
<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");
|
||||
|
Loading…
x
Reference in New Issue
Block a user