Skip to content

feat(windows): add native Windows WHPX hypervisor backend#1

Open
lilongen wants to merge 33 commits intoboxlite-ai:mainfrom
lilongen:feat/windows-whpx-support
Open

feat(windows): add native Windows WHPX hypervisor backend#1
lilongen wants to merge 33 commits intoboxlite-ai:mainfrom
lilongen:feat/windows-whpx-support

Conversation

@lilongen
Copy link
Copy Markdown

@lilongen lilongen commented May 5, 2026

Summary

Adds a complete Windows Hyper-V Platform (WHPX) hypervisor backend to libkrun, enabling native VM execution on Windows without WSL2. The implementation provides feature parity with the existing KVM (Linux) and Hypervisor.framework (macOS) backends.

Key capabilities:

  • Full x86-64 guest boot via WHPX API (windows-sys 0.61)
  • Userspace device emulation: PIC, PIT, IOAPIC, LAPIC, serial, CMOS RTC
  • virtio-mmio devices: blk (async worker), net, vsock, p9, rng, balloon
  • Multi-vCPU support (up to 4 vCPUs) with INIT-SIPI-SIPI AP bootstrap
  • Lock-free interrupt injection via SharedApicState + atomic pull_irr
  • ACPI tables (RSDP, RSDT, XSDT, MADT, DSDT with S5 shutdown)
  • Linux kernel boot with custom initrd and cmdline

Architecture

┌─────────────────────────────────────────────┐
│              libkrun API (FFI)              │
├─────────────────────────────────────────────┤
│  src/libkrun/src/windows_api.rs             │  ← krun_* FFI entry points
├─────────────────────────────────────────────┤
│  src/vmm/src/windows/                       │
│  ├── context.rs      VM configuration      │
│  ├── runner.rs       Main VMM event loop    │
│  ├── vcpu.rs         Per-vCPU state         │
│  ├── whpx.rs         WHPX API wrapper       │
│  ├── memory.rs       Guest physical memory  │
│  ├── insn.rs         x86 instruction decode │
│  ├── boot/           Kernel loading + ACPI  │
│  ├── devices/        Userspace device models│
│  │   ├── irq_chip    PIC → APIC transition │
│  │   ├── ioapic      I/O APIC emulation    │
│  │   ├── lapic       Local APIC + timer    │
│  │   ├── virtio/     Block, Net, Vsock...  │
│  │   └── ...         PIT, Serial, RTC      │
│  └── cmdline.rs      Kernel cmdline builder │
└─────────────────────────────────────────────┘

Key Design Decisions

  1. Userspace APIC emulation — WHPX's in-kernel APIC emulation crashes on some hardware (Win10 MBP 2014). We implement full LAPIC/IOAPIC in userspace with atomic lock-free interrupt delivery.

  2. Lock-free SharedApicState — Device threads raise interrupts via AtomicU64 IRR bitmask. vCPU threads pull pending interrupts without acquiring locks, avoiding contention in the hot path.

  3. ICR broadcast shorthand — Linux kernel uses "All Excluding Self" (shorthand 0b11) for IPI broadcast. Without handling this, only 2 vCPUs work. Fixed by parsing ICR bits 19:18 and dispatching to all APs.

  4. Async virtio-blk worker — Disk I/O runs on a dedicated thread with Windows overlapped I/O, preventing vCPU stalls during block operations.

  5. AF_UNIX sockets (not TCP) — Host-guest vsock traffic uses Unix domain sockets for security and performance, matching the macOS/Linux backends.

  6. HLT tiered sleep — Idle vCPUs use adaptive sleep (short spin → WaitForSingleObject) to balance latency vs CPU usage.

New Files (38 under src/vmm/src/windows/)

  • Boot: acpi.rs, loader.rs, mp_table.rs, params.rs, setup.rs
  • Core: context.rs, runner.rs, vcpu.rs, whpx.rs, memory.rs, insn.rs, cmdline.rs, types.rs, error.rs
  • Devices: manager.rs, irq_chip.rs, ioapic.rs, lapic.rs, pic.rs, pit.rs, serial.rs
  • Virtio: mmio.rs, queue.rs, block.rs, block_worker.rs, disk.rs, net.rs, vsock/mod.rs, vsock/connection.rs, vsock/packet.rs, p9/mod.rs, p9/filesystem.rs, p9/protocol.rs, rng.rs, balloon.rs

Modified Files

  • src/libkrun/src/lib.rs — cfg-gate Unix-only APIs, expose krun_start/krun_stop/krun_wait
  • src/libkrun/src/windows_api.rs — FFI bridge for Windows lifecycle
  • src/vmm/Cargo.toml — Windows dependencies (windows-sys, crossbeam, parking_lot)
  • include/libkrun.h — New function declarations
  • Cargo.lock — Updated dependency tree

Testing

Platform vm-bench (8 tests) net-test (8 tests)
Win11 (i5-1135G7) 8/8 PASS 8/8 PASS (4 vCPUs)
Win10 (i7-4770HQ) 8/8 PASS 8/8 PASS (4 vCPUs)
macOS/Linux Zero regression (fully cfg-gated)

Test Plan

  • CI passes on Linux (existing tests unaffected)
  • Windows build compiles with cargo build --target x86_64-pc-windows-msvc
  • Manual: boot_kernel example boots Linux on WHPX
  • Manual: vm-bench passes (create/exec/stop lifecycle)
  • Manual: net-test passes (guest networking, 4 vCPUs)

Stats

51 files changed, +27,501 / -261 (30 commits)

DorianZheng and others added 30 commits May 2, 2026 22:01
Add WHPX (Windows Hypervisor Platform) VMM backend enabling libkrun
to run on Windows alongside existing KVM and Hypervisor.framework backends.

- 33 new VMM files in src/vmm/src/windows/ (WHPX bindings, vCPU loop,
  memory management, interrupt controller, device emulation)
- C API entry points in src/libkrun/src/windows_api.rs
- Unix stub functions in lib.rs for krun_start/wait/stop/console/net

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- libkrun/Cargo.toml: split deps into cross-platform (log, vmm) and
  Unix-only (crossbeam, env_logger, libc, devices, polly, utils)
- libkrun/src/lib.rs: wrap entire Unix C API in `mod unix_api` gated by
  `#[cfg(not(target_os = "windows"))]`; move stub functions (krun_start,
  krun_wait, krun_stop, krun_get_console_output, krun_add_net) outside
  so they compile unconditionally
- vmm/Cargo.toml: split deps into cross-platform, Unix-only, and
  Windows-only (windows-sys, zerocopy, rand); gate cpuid to Unix x86_64
- vmm/src/lib.rs: gate all upstream VMM infrastructure (builder,
  device_manager, resources, vmm_config, terminal, worker, Vmm struct,
  Error enum) with `#[cfg(unix)]`; add `pub mod windows` for WHPX

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…Linux boot

Enable WHvPartitionPropertyCodeExtendedVmExits to intercept RDMSR/WRMSR
and CPUID instructions before they fault. Without this, unrecognized MSR
accesses during early kernel boot cause #GP → double fault → triple fault
(WHvRunVpExitReasonUnrecoverableException). Return safe defaults (0 for
MSR reads, host pass-through for CPUID) so the kernel proceeds past
hardware probing.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
PIT (8254 Programmable Interval Timer):
- Time-based decrementing counter via ns_accumulator (was returning
  static reload value, causing calibration loops to hang)
- BIOS defaults: counter 0 pre-programmed Mode 2, reload=0 (=65536,
  ~18.2 Hz) so timer interrupts fire before kernel programs the PIT
- Tick all 3 counters (not just counter 0) so counter 2 reads work
  for pit_calibrate_tsc()
- Handle reload=0 as 65536 per 8254 specification

Device manager:
- Port 0x61 bit 5 toggles on each read (was static 0x20), required
  by Linux pit_calibrate_tsc() which polls for bit changes
- i8042 PS/2 controller stubs (ports 0x60/0x64 return 0x00) to
  prevent driver spin loops on empty buffers

Runner (vCPU loop):
- Hyper-V CPUID masking: leaf 1 ECX bit 31 cleared, leaves
  0x40000000-0x400000FF return zeros — prevents guest from using
  broken Hyper-V enlightenments (synthetic timers, SynIC)
- Progress reporting every 5 seconds with IO port statistics,
  MSR/CPUID counters, and console output size
- GVA-to-GPA page table walker for debugging (unused but available)

Smoke test:
- examples/boot_kernel.rs: standalone binary using vmm runner directly
- Usage: boot_kernel.exe <vmlinuz> [initrd] [-- extra-cmdline-args]

Verified: Linux 6.12.80-0-virt boots to interactive shell in ~5 seconds
on Win10 WHPX (MacBook Pro 2014, Haswell).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- boot_kernel.rs: add --disk <path> CLI flag for virtio-blk testing
- cmdline.rs: move nohyperv/lpj/nokaslr from user cmdline to BASE_CMDLINE
  (always needed for WHPX, prevents Hyper-V enlightenment stalls)
- runner.rs: minor comment cleanup in CPUID masking

Tested on Win10 WHPX:
- Kernel boot without disk: OK (shell prompt in ~5s)
- Kernel boot with 64MB ext4 disk: virtio_blk detected [vda],
  EXT4-fs mounted r/w successfully, 168 MMIO exits

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Implement krun_set_root_disk_remount on Windows (was -ENOSYS stub) to
store root_disk_device and root_disk_fstype in VmContext. Extend
build_kernel_cmdline() to accept root device override, init path, and
init argv -- producing cmdlines like:

  root=/dev/vdb rootfstype=ext4 rw init=/boxlite/bin/boxlite-guest
  ... -- --listen vsock://2695 --notify vsock://2696

This enables the full box lifecycle on WHPX where there is no firmware
to mount rootfs and exec the guest agent automatically.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…l example

Enable Level 2 smoke testing of the new cmdline wiring on WHPX:
  boot_kernel.exe vmlinuz --disk rootfs.img --init /bin/sh
  boot_kernel.exe vmlinuz --disk rootfs.img --root /dev/vda --fstype ext4 --init /init --argv --flag

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The Linux kernel's virtio-mmio driver rejects devices with vendor_id == 0,
causing virtio-blk device enumeration to fail silently. Set vendor ID to
the standard QEMU value (0x554D4551). Also add debug logging to
virtio-blk error paths for easier diagnosis of I/O failures.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Vsock: add connect_targets HashMap + connect_to() for guest-initiated
  outbound TCP connections (guest vsock → host TCP). Previously only
  host→guest (listen_on) was supported. 4 new tests.
- Device manager: dispatch vsock ports by VsockPort.listen flag
  (true=listen_on, false=connect_to). Add second virtio-blk device
  (slot 4) for guest rootfs disk.
- Boot loader: split E820 memory map around MMIO region when RAM > 3.25GB
  to prevent kernel using device addresses as RAM. 2 new tests.
- Memory: add MMIO_REGION_SIZE constant, split GuestMemory into two
  regions when RAM overlaps VIRTIO_MMIO_BASE.
- Runner: add eprintln progress reporting for shim capture (log::* may
  be silently dropped without log→tracing bridge).
- boot_kernel: add --vsock-listen and --vsock-connect CLI flags.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Add 16-byte TX FIFO to serial device: batch output flushes on
  newline, buffer full, IIR read, or FCR reset. Reduces per-byte
  VM exits during kernel boot console output.
- Format PIT time-based counter code for readability.
- Standardize imports across virtio devices (alphabetical ordering,
  error types first).
- Improve code formatting in whpx.rs, builder.rs, and virtio modules.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add minimal ACPI tables (RSDP, RSDT, FADT, DSDT ~227 bytes) to guest
memory so Linux discovers PM1a_CNT at port 0x604. When the kernel
writes S5 sleep type (SLP_EN=1, SLP_TYP=5), the VMM detects shutdown
instantly instead of waiting for the HLT loop timeout.

Key changes:
- New acpi.rs: generates ACPI tables with \_S5_ AML package at 0xE0000
- loader.rs: writes ACPI tables to guest memory, adds E820_ACPI entry
- manager.rs: PM1a_CNT/EVT port handlers, shutdown_requested flag
- runner.rs: checks shutdown_requested after IO out, MAX_HALTS 5000→50
- cmdline.rs: removes noacpi, adds quiet/verbose modes
- context.rs: verbose field for debug cmdline selection
- boot_kernel.rs: --verbose CLI flag

Results: VM exits 27K→13.5K (50% reduction), shutdown 5s→0ms.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
… routing

Add host-to-guest connection initiation for vsock:
- VsockHeader::new_request() for REQUEST packets from host to guest
- VsockConnection::initiate_connect() state transition (Idle -> Connecting)
- poll_tcp_listeners() accepts incoming TCP, sends REQUEST to guest
- Skip TCP reads on non-Connected streams during handshake

Improve vsock port routing in DeviceManager:
- Support host_path as "host:port" format (from krun_add_vsock_port2 API)
- Fallback chain: explicit host_tcp_port > host_path > vsock port number

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…, diagnostics

Fix three root causes of WHPX flakiness, achieving 100% pass rate on
both Win10 and Win11 (previously ~40%):

PIC 8259A priority masking (40% → 80%):
- Fix pending_irq() to implement proper priority blocking: when an IRQ
  is in-service, all equal-or-lower-priority IRQs are blocked
- Previously only blocked re-delivery of the same IRQ (irr & !imr & !isr)
- Root cause: PIT (IRQ 0) and vsock (IRQ 6) both stuck in-service
  (ISR=0x41), causing kernel handler deadlock

HLT clear_halt — QEMU-style active wake (90% → 100%):
- On HLT exit, poll devices before sleeping; if PIC has pending
  interrupt, clear halt suspend via WHvRegisterInternalActivityState
- Prevents lost wakeups where guest sleeps through pending vsock data
- Matches QEMU's whpx-all.c HLT handling strategy

Safety and diagnostics:
- Increase MAX_HALTS from 50 to 50,000 (guest HLTs normally in idle loop)
- Add vcpu.run() error handling with exit reason tracking
- Add MMIO decode and HRESULT error context logging
- Add vsock TCP nodelay, write retry loop, connection state logging
- Add PIC master_state() diagnostic accessor
- Track and report exit reason (ACPI_SHUTDOWN, HALT_STOP_REQUESTED, etc.)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- CMOS RTC: use host UTC time with proper BCD encoding (to_bcd).
  Previous hardcoded decimal values caused guest to read year 2019
  instead of 2026, breaking SSL certificate validation.
- Virtio-MMIO: handle byte/word config space reads by aligning to
  4-byte boundary and extracting the correct byte. Linux's virtio-mmio
  driver reads MAC address one byte at a time via readb(); unaligned
  reads previously returned 0, causing wrong MAC and NO-CARRIER.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…logging

Increase the per-poll TCP read buffer from 4096 to 65536 bytes.
This improves vsock throughput for large data transfers (e.g. container
image layers, HTTP downloads) by reducing the number of poll cycles
needed per transfer.

Also add trace-level logging for guest→host packets and TCP poll activity
to aid future debugging without impacting performance at info level.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
… fixes

Add async block I/O worker infrastructure that moves disk reads/writes
to a dedicated thread via mpsc channels. This prevents heavy disk I/O
from starving vsock/net devices in the vCPU loop.

However, the async worker is DISABLED on Windows/WHPX because the worker
thread's raw pointer writes to guest memory conflict with WHPX memory
tracking, causing ~60% boot failure rate. Sync disk I/O remains the
default and provides 100% boot reliability (verified 20/20 on Win10).

Other changes in this commit:
- HLT handler: replace clear_halt() with inject_interrupt() for
  more reliable interrupt delivery on WHPX
- Add APIC emulation guard comment (broken on Win10 MBP 2014)
- Add diagnostic HLT counters and periodic logging
- GuestMemory implements GuestMemoryAccessor directly (Arc-compatible)
- whpx: add request_interrupt() method and warn-level logging
- mmio: add poll_backend() for async completion draining
- disk: add Send bound to DiskBackend trait

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Enable async virtio-blk I/O on WHPX with two critical fixes:

1. Pending interruption guard: Read WHvRegisterPendingInterruption
   before injecting new interrupts. Without this, a Cancelled vCPU
   exit could leave a previous injection undelivered, and the next
   injection would silently overwrite it — permanently sticking the
   PIC ISR bit (guest never sends EOI for a lost interrupt).

2. Spurious cascade guard: In Pic::acknowledge(), only call
   master.acknowledge() when the slave has a real deliverable IRQ.
   Previously, spurious cascades (slave all-masked) would set ISR
   bit 2 with no corresponding interrupt delivery.

Also: Plan B worker architecture (worker thread never touches guest
memory — all guest mem reads/writes on vCPU thread), slave PIC
diagnostics, flush bytes_written fix.

Win10 validated: 5/5 sync + 5/5 async PASS.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Replace PIC-only interrupt routing with a full IOAPIC + LAPIC + IrqChip
architecture. This enables level-triggered interrupts, 24 IRQ pins, and
lays the groundwork for multi-vCPU support (Iter 3).

New files:
- ioapic.rs: 24-pin I/O APIC with redirection table and MMIO interface
- lapic.rs: Local APIC with IRR/ISR priority logic and timer support
- irq_chip.rs: Coordinator wiring PIC + IOAPIC + LAPIC with auto PIC→APIC
  mode transition

Key changes:
- MADT ACPI table added for Linux kernel APIC discovery
- Remove noapic/nolapic from kernel cmdline to enable APIC mode
- Manager routes MMIO reads/writes to IOAPIC (0xFEC00000) and LAPIC
  (0xFEE00000) address ranges
- Runner uses IrqChip for interrupt injection with LAPIC priority checks
- IRQ 0→GSI 2 remapping per standard x86 convention (MADT ISO entry)
- PIC retained for legacy boot compatibility; IrqChip auto-switches when
  guest enables LAPIC SVR + IOAPIC has unmasked entries

Verified: Win10 vm-bench 8/8 PASS, Win11 vm-bench 8/8 PASS,
net-test 8/8 PASS on both machines.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…ed runner)

- LAPIC: per-vCPU instances with ICR register for IPI dispatch
  (INIT, SIPI, Fixed interrupt delivery modes)
- IrqChip: multi-LAPIC array with per-vcpu_id routing
- IOAPIC: returns (vector, dest_apic_id) from service_irq
- DeviceManager: vcpu_id parameter threading, IpiAction returns
- Runner: BSP + AP threads via std::thread::scope, Arc<Mutex<DeviceManager>>,
  INIT-SIPI-SIPI protocol with Condvar wake, per-vCPU stats
- MADT: dynamic N-LAPIC entry generation for num_vcpus
- Cmdline: removed nosmp for SMP kernel boot
- Loader: num_vcpus parameter threading to ACPI tables
- WHPX: VcpuCanceller Clone, set_ap_initial_regs for real-mode AP startup
- CPUID leaf 1: topology injection (max APIC IDs, initial APIC ID)
- MSR 0x1B: IA32_APIC_BASE with enable + BSP flag
- Hyper-V CPUID leaves masked to zeros

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add two new virtio devices for improved guest quality:

- virtio-rng (slot 5, IRQ 10): Provides host entropy to guest via
  /dev/hwrng using OsRng. Purely guest-initiated, no async worker.

- virtio-balloon (slot 6, IRQ 11): Protocol-only dynamic memory
  management with inflate/deflate queues. Actual memory discard
  deferred to future iteration.

Also adds write_config() to VirtioDeviceBackend trait (default no-op)
for devices with writable config space (balloon needs it for 'actual').

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…ttle

Performance + production polish for Windows WHPX VMM:

- HLT sleep: replace flat 1ms sleep with tiered strategy (50 spin-yield
  iterations then 200µs sleep), reducing interrupt delivery latency ~5x
- Diagnostic logging: replace all eprintln! with structured log::info!/
  log::warn!/log::debug! using "whpx::diag" target, respecting RUST_LOG
- Diagnostic file: clean up temp whpx-diag.log on normal VM exit
- IPI diagnostics: add elapsed timestamps to IPI dispatch log entries
- LAPIC timer throttle: skip LAPIC timer ticks when <500µs elapsed,
  reducing wasted CPU (PIT timer still fires every tick)

Warm exec improved: Win11 14→5.5ms (-61%), Win10 45→33ms (-27%).
vm-bench 8/8 PASS, net-test 8/8 PASS on both platforms.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Enable copy-on-write (COW) disk chains in the Windows VMM by supporting
QCOW2 backing file references. Unallocated clusters now delegate reads
to the backing file instead of returning zeros, enabling thin COW overlays
that eliminate expensive ~256MB disk copies per box.

Also includes formatting cleanup from cargo fmt.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Change IrqChip.lapics from Vec<LocalApic> to Vec<Arc<Mutex<LocalApic>>>
to eliminate cross-vCPU lock contention during LAPIC MMIO access.

Add fast path in runner that bypasses DeviceManager lock entirely for
per-vCPU LAPIC reads (all offsets) and simple writes (TPR, ICR High,
LVT Timer, Initial Count, Divide Config). Writes with cross-device side
effects (EOI, SVR, ICR Low) still go through the DeviceManager path.

Optimize AP interrupt injection and HLT spin-yield to check per-LAPIC
first (cheap) before acquiring DeviceManager lock (expensive).

This resolves the 4+ vCPU hang where SMP timer calibration caused all
vCPU threads to contend the single DeviceManager mutex for CCR reads,
starving BSP's tick_and_poll() and blocking I/O completions.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Lock-free interrupt delivery:
- SharedApicState with atomic pending_irr for cross-vCPU interrupt
  injection without DeviceManager lock contention
- try_inject_interrupt_fast() bypasses lock for common case
- LapicWriteFastResult for inline ICR/EOI handling in vCPU loop
- pull_irr after tick_and_poll to catch device-raised interrupts

CPUID topology override:
- Intercept leaf 0xB/0x1F (Extended Topology Enumeration) to return
  correct guest topology instead of host passthrough
- Intercept leaf 4 (Deterministic Cache Parameters) to match guest
  vCPU count in max_cores and max_threads_sharing fields
- Add input_rcx parameter to handle_cpuid() — guest's original ECX
  (sub-leaf number) is distinct from WHPX's default_rcx (output)

MMIO diagnostic counters for tight loop detection (BSP hang analysis).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Fix 3+ vCPU BSP hang caused by missing ICR destination shorthand
handling in parse_icr(). Linux kernel uses "All Excluding Self"
(bits 19:18 = 0b11) to broadcast wakeup IPI to all APs during SMP
init. Previously only single-target dispatch from ICR High was
implemented, so APs 2+ never received the wakeup.

Changes:
- Add BroadcastInterrupt variant to IpiAction enum
- Parse ICR destination shorthand (Self/All-Incl/All-Excl) in parse_icr()
- Handle BroadcastInterrupt in BSP and AP fast paths (lock-free)
- Handle BroadcastInterrupt in dispatch_ipi() slow path
- Add vcpu_running flags to guard timer cancel (only cancel running vCPUs)
- Add periodic AP progress logging (RIP + stats every 500 Cancelled exits)
- Add cancelled_count and cpuid_count to VcpuStats
- Add AP exit summary on shutdown/max_exits

Tested: Win11 (T14) and Win10 (MBP 2014) — vm-bench 8/8, net-test 8/8
at 4 vCPUs.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- vsock device: TcpListener/TcpStream → UnixListener/UnixStream
  (uds_windows on Windows, std::os::unix::net on Unix)
- listen_on() now takes socket_path instead of host_port
- connect_to() uses UnixStream::connect instead of TcpStream::connect
- Remove set_nodelay() (not applicable to Unix sockets)
- Rename poll_tcp_listeners/poll_tcp_streams → poll_listeners/poll_streams
- manager.rs: simplify vsock config to pass socket paths directly
- net.rs: replace TcpTransport with UdsTransport (Windows)
- All 15+ vsock tests rewritten for Unix sockets

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…ation

Move devices, polly, and utils crates to [target.'cfg(unix)'.dependencies]
in libkrun/Cargo.toml since these depend on nix, vm-memory, and other
Unix-only crates that fail to compile on Windows. The Windows WHPX backend
has its own self-contained device implementations and never uses these crates.

Also fix cpuid dependency in vmm/Cargo.toml to include package name specifier
(krun-cpuid) lost during rebase.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The enable_tsi field was replaced with tsi_flags: TsiFlags but the
getter still referenced self.enable_tsi, causing infinite recursion.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
lile and others added 3 commits May 5, 2026 21:12
- Run cargo fmt to fix import ordering (cpuid, muxer, lib.rs, windows/)
- Add `efi = []` to vmm/Cargo.toml to resolve "unexpected cfg condition
  value" clippy error on builder.rs:91

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Fix import ordering in cpuid/src/common.rs for rustfmt 1.95
- Add back devices dev-dependency with test_utils feature (gated to
  cfg(unix)) so DummyIrqChip is available for vmm unit tests

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The boot_kernel example uses vmm::windows::* modules and env_logger
(Windows dev-dep), but Cargo auto-discovers examples and tries to
compile them on all platforms. Add cfg(windows) gates and a stub
main() for non-Windows platforms.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@@ -0,0 +1,896 @@
//! Virtio-net device backend (virtio spec v1.2 Section 5.1).
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why not just resue libkrun devices?

Comment thread include/libkrun.h
uint32_t features,
uint32_t flags);

/**
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

there is already krun_disable_implicit_vsock for disabling tsi

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants