Skip to content

ci: a cold boot's time sample exceeded 100 µs, and a clone's repair failed with 195, on azure-windows-1 (flaky NVX microVM tests / Windows / WHP / Runtime adapter) #1309

Closed

Description

Summary

Two runs of NVX microVM tests / Windows / WHP / Runtime adapter failed 14 minutes apart on azure-windows-1, in different scenarios, each because a guest failed time ABI 2 and powered its VM off. Neither head changes any time code.

At a cold boot and at a clone's repair alike, the guest takes up to 3 time samples. It accepts one only if OpenVMM paired host UTC with the guest TSC within 100 µs; if none qualifies, the guest powers off (Table 3.10). Incident 2 shows a sample over the bound. Incident 1's status most likely comes from the same check failing during the repair, though no log names the check (see Evidence). In the same two workflow runs, the WHP benchmark runner, azure-windows-5, paired its samples within 136 and 139 ns.

Neither change touches time:

#1302's identical tree passed its next merge group on azure-windows-6. azure-windows-1 passed WHP jobs at 01:16Z, before the incidents, and at 02:00Z and 02:11Z, after them.

Incidents

1. Clone repair, merge group of #1302 (2026-11-06 01:34Z)

  • Workflow: CI run 42144050826, attempt 1, merge_group.

  • Head: c41a9b8c3a52e9fdcfcc8f776c3bf804fc8e2879, ci: run pushes to feature/nvx-refactor #1302's 6224fb785 on dev's 4cfe8330e. OpenVMM 14dc4116ec7e57567633c4b7b07892aca3a58522.

  • Failed job: NVX microVM tests / Windows / WHP / Runtime adapter on azure-windows-1, step Run runtime adapter scenarios on Windows. vm_clone passed 34 of its 35 tests.

  • Failure, at vm_clone.rs:1492:

    left:  ["repair", "repair-status", "activation", "event", "195", "exited"]
    right: ["request", "unusable-root", "activation", "activating", "54", "exited"]
    

    The start printed:

    {"downtime": "10336688075", "failure.code": "exited", "failure.evidence": "repair-status", "failure.outcome": "repair", "failure.progress": "event", "failure.stage": "activation", "failure.status": "195", "failure.teardown": "exited", "generation": "1", "lease": "42197786ea8a4fe185cd79818a8348d5", "pid": "9868", "quarantined": "no", "released": "42197786ea8a4fe185cd79818a8348d5", "source": "monotonic"}
    
  • Downstream:

2. Cold boot, pull-request run of #1303 (2026-11-06 01:47Z)

  • Workflow: CI run 42144804527, attempt 1, pull_request.

  • Head: c96ceaaee37ee97230a2fbc3402c5b9bf88119f4. OpenVMM 6fb64731f03314a3c5ee634d3c85d6782a5babe0, incident 1's pin plus 3 commits in serial_socket and the virtio_console tests only.

  • Failed job: NVX microVM tests / Windows / WHP / Runtime adapter on azure-windows-1, the same step. vm_layered passed 42 of its 43 tests.

  • Failure: the launch of a_denied_network_lets_no_probe_through exited 1 with cannot attach to the VM: the broker closed the NVXS session. The VMM's log ended:

    NVX-TIME-ABI-VIOLATION: v=1 code=G_CONFORMANCE_C12 source=conformance phase=boot generation=0 boottime_ns=2251650395 detail="time sample uncertainty 119213 ns exceeds 100000 ns"
       3.487992600s  INFO openvmm_entry::vm_controller:  guest halted reason=PowerOffWithStatus { code: c1 }
    

Runner validation passed H1 to H4 in both jobs; H4 found azure-windows-1's TSC rate in agreement with QueryPerformanceCounter. No check measures how long OpenVMM takes to pair a sample.

Evidence

History

The 300 CI runs from 2026-11-02 08:37Z to 2026-11-06 02:12Z:

  • The WHP runtime-adapter job completed 121 times and failed 3.
    • Two failures are these, on azure-windows-1, which passed the job 16 times.
    • The third was on azure-windows-4 (run 42095876865): a network check, vm_layered an_allow_rule_lets_only_its_destination_through, with no time violation.
  • Of the 33 jobs that failed in those runs, on every backend, only these two logged a time-ABI violation.

Root cause

Probably a transient condition of azure-windows-1 around 01:34Z and 01:47Z on 2026-11-06, in which OpenVMM could not pair host UTC with the guest TSC within 100 µs in 3 tries. The guest and OpenVMM did what time ABI 2 specifies.

What delayed the pairing is unknown. A stall of the runner VM's vCPUs would explain it, whether from contention with the suite's parallel VMs, a noisy neighbor, or host maintenance such as #768's live migration.

Impact

Suggested next steps

  1. Find what azure-windows-1 went through from 01:30Z to 01:50Z on 2026-11-06: the Azure activity log of its VM (maintenance, live migration), its vCPU wait time, and its load, as ci: track azure-mshv-1's intermittent H4 failures after a live migration to a host with an unstable clock #768 did for azure-mshv-1.
  2. Record the uncertainty of accepted samples on the general runners, as the platform job's log does, to learn how close their suites come to the bound under parallel load.
  3. Make a clone's 195 attributable:
    • Keep the time-ABI violation of a clone's guest where the host can report it.
    • Upload the runtime adapter's VMM logs when its job fails.
  4. If the general runners come close to the bound in normal runs, don't loosen the tests. Instead, either:
    • qualify the runners for the bound, as runner validation's H4 does for the TSC rate; or
    • revisit the bound or the number of attempts in the time ABI's design.

Related

Activity

  1. ppenna commented on Nov 6, 2026

    @ppenna
    ContributorAuthor

    Update on 2026-11-06

    A second investigation of incident 2 (run 42144804527) agrees with the root cause above. There's no new occurrence: in the 7 CI runs since 02:00Z, no job failed, and the WHP runtime-adapter job passed 4 times, once on azure-windows-1 at 02:54Z. #1303's head is still c96ceaae, with no rerun, so its Required status check stays red until the job is rerun.

    Three corrections to the description, and one addition.

    Corrections

    Addition: on WHP, one measurement at a VM's start widens all of its samples

    All 3 samples can then exceed 100 µs in two ways:

    1. Every one of the 8 reads at the start is slow. Every sample of the VM is then wide, and the guest's 3 attempts can't help, since they all reuse the offset. To explain incident 2 alone, each read would have taken at least 236 µs, about 2 ms for all 8.
    2. Each sample is delayed. The guest also adds half the time between its TSC reads around its clock read, and 2,000 ppm of the time from OpenVMM's pairing to that read, so a vCPU that resumes 50 ms after its port exit adds 100 µs. All 3 samples would need such a delay.

    OpenVMM's log tells them apart. At each start it logs time ABI: guest TSC offset with uncertainty_cycles. For incident 2, about 330,000 cycles (118 µs at azure-windows-1's 2.79 GHz) would mean the offset, and about 24,000 to 35,000 would mean per-sample delays. That line is what step 3 needs to keep.

    If the offset is the cause, more attempts in the guest (step 4) can't help. The fix would belong in OpenVMM, for example measuring the offset again while its tightest read is still wide.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

bugSomething isn't working

Type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions