[libvirt] [PATCH 3/3] qemu: hyperv: Add support for reference time couter enlightenment

Paolo Bonzini pbonzini at redhat.com
Fri Feb 7 11:03:58 UTC 2014


Il 05/02/2014 12:02, Peter Krempa ha scritto:
> Add a new <timer> for the HyperV reference time counter enlightenment
> for Windows guests.
>
> This feature provides a paravirtual approach to track timer events for
> the quest (similar to kvmclock).

RTC can be confusing because the same acronym expands to both "real-time 
clock" and "reference time counter".

By the way, the same <timer> will drive two things: the reference time 
counter, and the reference TSC page.  In current kernels, the reference 
TSC page just tells the guest "use the reference time counter", but this 
can be changed in the future without breaking the guest ABI.

So, what about naming it hv_clock or hyperv_clock or hyperv_ref?

Paolo

> ---
>  docs/formatdomain.html.in                          |  7 ++++-
>  docs/schemas/domaincommon.rng                      |  5 +++-
>  src/conf/domain_conf.c                             |  6 +++--
>  src/conf/domain_conf.h                             |  1 +
>  src/qemu/qemu_command.c                            | 30 ++++++++++++----------
>  .../qemuxml2argv-clock-timer-hyperv-rtc.args       |  5 ++++
>  .../qemuxml2argv-clock-timer-hyperv-rtc.xml        | 26 +++++++++++++++++++
>  tests/qemuxml2argvtest.c                           |  1 +
>  tests/qemuxml2xmltest.c                            |  1 +
>  9 files changed, 65 insertions(+), 17 deletions(-)
>  create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.args
>  create mode 100644 tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.xml
>
> diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in
> index fd02864..451ce8f 100644
> --- a/docs/formatdomain.html.in
> +++ b/docs/formatdomain.html.in
> @@ -1367,7 +1367,12 @@
>              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 "hyperv_rtc"
> +            (qemu - <span class="since">since 1.2.2</span>).
> +
> +            The <code>hyperv_rtc</code> timer adds support for the
> +            "reference time counter" feature for guests running the
> +            Microsoft Windows operating system.
>            </dd>
>            <dt><code>track</code></dt>
>            <dd>
> diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng
> index 12fc0db..96e62d3 100644
> --- a/docs/schemas/domaincommon.rng
> +++ b/docs/schemas/domaincommon.rng
> @@ -915,7 +915,10 @@
>          </group>
>          <group>
>            <attribute name="name">
> -            <value>kvmclock</value>
> +            <choice>
> +              <value>kvmclock</value>
> +              <value>hyperv_rtc</value>
> +            </choice>
>            </attribute>
>          </group>
>        </choice>
> diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
> index b6c984b..33b5bee 100644
> --- a/src/conf/domain_conf.c
> +++ b/src/conf/domain_conf.c
> @@ -726,7 +726,8 @@ VIR_ENUM_IMPL(virDomainTimerName, VIR_DOMAIN_TIMER_NAME_LAST,
>                "rtc",
>                "hpet",
>                "tsc",
> -              "kvmclock");
> +              "kvmclock",
> +              "hyperv_rtc");
>
>  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_HYPERV_RTC) {
>              if (timer->tickpolicy != -1) {
>                  virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
>                                 _("timer %s doesn't support setting of "
> diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
> index d8f2e49..300ba26 100644
> --- a/src/conf/domain_conf.h
> +++ b/src/conf/domain_conf.h
> @@ -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_HYPERV_RTC,
>
>      VIR_DOMAIN_TIMER_NAME_LAST
>  };
> diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
> index eef65ae..bc5219c 100644
> --- a/src/qemu/qemu_command.c
> +++ b/src/qemu/qemu_command.c
> @@ -6728,20 +6728,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_HYPERV_RTC &&
> +                   timer->present) {
> +            virBufferAsprintf(&buf, "%s,hv_time",
> +                              have_cpu ? "" : default_model);
>              have_cpu = true;
> -            break;
>          }
>      }
>
> @@ -8003,8 +8006,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,
> @@ -8013,7 +8015,9 @@ qemuBuildCommandLine(virConnectPtr conn,
>              goto error;
>
>          case VIR_DOMAIN_TIMER_NAME_KVMCLOCK:
> -            /* This is handled when building -cpu.  */
> +        case VIR_DOMAIN_TIMER_NAME_HYPERV_RTC:
> +            /* Timers above are handled when building -cpu.  */
> +        case VIR_DOMAIN_TIMER_NAME_LAST:
>              break;
>
>          case VIR_DOMAIN_TIMER_NAME_RTC:
> diff --git a/tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.args b/tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.args
> new file mode 100644
> index 0000000..1905875
> --- /dev/null
> +++ b/tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.args
> @@ -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
> diff --git a/tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.xml b/tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.xml
> new file mode 100644
> index 0000000..47c7c42
> --- /dev/null
> +++ b/tests/qemuxml2argvdata/qemuxml2argv-clock-timer-hyperv-rtc.xml
> @@ -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='hyperv_rtc' 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>
> diff --git a/tests/qemuxml2argvtest.c b/tests/qemuxml2argvtest.c
> index a25264e..1394d68 100644
> --- a/tests/qemuxml2argvtest.c
> +++ b/tests/qemuxml2argvtest.c
> @@ -628,6 +628,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);
> diff --git a/tests/qemuxml2xmltest.c b/tests/qemuxml2xmltest.c
> index 41d1904..e12a0ab 100644
> --- a/tests/qemuxml2xmltest.c
> +++ b/tests/qemuxml2xmltest.c
> @@ -159,6 +159,7 @@ mymain(void)
>      DO_TEST("cpu-kvmclock");
>      DO_TEST("cpu-host-kvmclock");
>      DO_TEST("kvmclock");
> +    DO_TEST("clock-timer-hyperv-rtc");
>
>      DO_TEST("cpu-eoi-disabled");
>      DO_TEST("cpu-eoi-enabled");
>




More information about the libvir-list mailing list