Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/xen/xen Rearm the Xen timer on resume.



details:   https://anonhg.NetBSD.org/src/rev/f4872049f466
branches:  trunk
changeset: 833538:f4872049f466
user:      riastradh <riastradh%NetBSD.org@localhost>
date:      Sat Jun 30 14:59:38 2018 +0000

description:
Rearm the Xen timer on resume.

This just moves the timer-arming logic from xen_initclocks into
xen_resumeclocks so that it runs on resume too.

I hypothesize that this is necessary for Xen to resume.  Otherwise,
how could the one-shot timer possibly by rearmed?  On the other hand,
it is conceivable that something automatically rearms it.

This also reorders the initialization so that we establish a timer
interrupt handler first, and _then_ arm the timer.  If the order
matters, it is hard to imagine that the other way is correct:
conceivably, the interrupt could arrive before we've established the
handler, and then there's nothing to rearm it.

Whether this is _sufficient_ for Xen to resume, I don't know.
Symptoms recently reported in
<https://mail-index.netbsd.org/port-xen/2018/06/15/msg009207.html>
look different from how I would expect this to manifest, which is as
a system wedged because there's no no hardclock activity.

ok cherry

diffstat:

 sys/arch/xen/xen/clock.c |  40 ++++++++++++++++++++--------------------
 1 files changed, 20 insertions(+), 20 deletions(-)

diffs (96 lines):

diff -r 4b2ef342600a -r f4872049f466 sys/arch/xen/xen/clock.c
--- a/sys/arch/xen/xen/clock.c  Sat Jun 30 14:55:13 2018 +0000
+++ b/sys/arch/xen/xen/clock.c  Sat Jun 30 14:59:38 2018 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: clock.c,v 1.69 2018/06/30 14:21:19 riastradh Exp $     */
+/*     $NetBSD: clock.c,v 1.70 2018/06/30 14:59:38 riastradh Exp $     */
 
 /*-
  * Copyright (c) 2017, 2018 The NetBSD Foundation, Inc.
@@ -36,7 +36,7 @@
 #endif
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: clock.c,v 1.69 2018/06/30 14:21:19 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: clock.c,v 1.70 2018/06/30 14:59:38 riastradh Exp $");
 
 #include <sys/param.h>
 #include <sys/types.h>
@@ -740,8 +740,8 @@
 /*
  * xen_resumeclocks(ci)
  *
- *     Start handling the Xen timer event on the CPU of ci.  Caller
- *     must be running on and bound to ci's CPU.
+ *     Start handling the Xen timer event on the CPU of ci.  Arm the
+ *     Xen timer.  Caller must be running on and bound to ci's CPU.
  *
  *     Actually, caller must have kpreemption disabled, because that's
  *     easier to assert at the moment.
@@ -751,6 +751,7 @@
 {
        char intr_xname[INTRDEVNAMEBUF];
        int evtch;
+       int error;
 
        KASSERT(ci == curcpu());
        KASSERT(kpreempt_disabled());
@@ -772,6 +773,21 @@
 
        aprint_verbose("Xen %s: using event channel %d\n", intr_xname, evtch);
 
+       /* Disarm the periodic timer on Xen>=3.1 which is allegedly buggy.  */
+       if (XEN_MAJOR(xen_version) > 3 || XEN_MINOR(xen_version) > 0) {
+               error = HYPERVISOR_vcpu_op(VCPUOP_stop_periodic_timer,
+                   ci->ci_cpuid, NULL);
+               KASSERT(error == 0);
+       }
+
+       /* Pretend the last hardclock happened right now.  */
+       ci->ci_xen_hardclock_systime_ns = xen_vcputime_systime_ns();
+
+       /* Arm the one-shot timer.  */
+       error = HYPERVISOR_set_timer_op(ci->ci_xen_hardclock_systime_ns +
+           NS_PER_TICK);
+       KASSERT(error == 0);
+
        /* We'd better not have switched CPUs.  */
        KASSERT(ci == curcpu());
 }
@@ -848,7 +864,6 @@
 xen_initclocks(void)
 {
        struct cpu_info *ci = curcpu();
-       int error;
 
        /* If this is the primary CPU, do global initialization first.  */
        if (ci == &cpu_info_primary) {
@@ -865,9 +880,6 @@
 #endif
        }
 
-       /* Pretend the last hardclock happened right now.  */
-       ci->ci_xen_hardclock_systime_ns = xen_vcputime_systime_ns();
-
        /* Attach the event counters.  */
        evcnt_attach_dynamic(&ci->ci_xen_cpu_tsc_backwards_evcnt,
            EVCNT_TYPE_INTR, NULL, device_xname(ci->ci_dev),
@@ -888,18 +900,6 @@
            EVCNT_TYPE_INTR, NULL, device_xname(ci->ci_dev),
            "missed hardclock");
 
-       /* Disarm the periodic timer on Xen>=3.1 which is allegedly buggy.  */
-       if (XEN_MAJOR(xen_version) > 3 || XEN_MINOR(xen_version) > 0) {
-               error = HYPERVISOR_vcpu_op(VCPUOP_stop_periodic_timer,
-                   ci->ci_cpuid, NULL);
-               KASSERT(error == 0);
-       }
-
-       /* Arm the timer.  */
-       error = HYPERVISOR_set_timer_op(ci->ci_xen_hardclock_systime_ns +
-           NS_PER_TICK);
-       KASSERT(error == 0);
-
        /* Fire up the clocks.  */
        xen_resumeclocks(ci);
 }



Home | Main Index | Thread Index | Old Index