A Failure Report: Single-GPU Passthrough on Arrow Lake with the xe Driver
Intel Arc + xe + VFIO: A Single-GPU Passthrough Failure Report

A failed but useful VFIO experiment with Arrow Lake, the Linux xe driver, QEMU/KVM, libvirt, and Windows 11.
We did not learn that it simply does not work.
We learned where it stops working.
That is the main reason I am writing this down.
This was an attempt to pass through the integrated Intel Arc GPU of a modern Intel Core Ultra laptop to a Windows 11 virtual machine. It did not end with a working gaming VM or a clean success story. It ended with Intel’s Windows driver seeing the GPU, installing correctly, and then failing with Code 43.
That failure is still useful.
Most VFIO writeups are success reports. This one is closer to a lab notebook.
Context
This experiment was done on a laptop with:
CPU: Intel Core Ultra 9 285H
GPU: Intel Arrow Lake-P / Arc Pro 130T/140T
PCI ID: 8086:7d51
Host GPU driver: xe
Host OS: Fedora-based Linux
Display manager: COSMIC Greeter
Guest OS: Windows 11
Virtualization stack: KVM/QEMU/libvirt/virt-manager
I am not a VFIO expert. I had basic VM knowledge, some Linux comfort, and enough curiosity to try something that was probably not going to be plug-and-play. I used ChatGPT as a technical debugging partner during the process: reading logs, forming hypotheses, and deciding what to try next.
The interesting part of this setup was not “Windows 11 in a VM.” That part was straightforward.
The interesting part was this combination:
Intel Arc integrated graphics
Arrow Lake mobile platform
Linux xe driver
Single-GPU laptop passthrough
Windows 11 guest
Internal laptop panel
Most single-GPU passthrough guides target Nvidia or AMD desktop GPUs. Some Intel iGPU material exists, but often for older generations, older i915-based setups, or different use cases.
This was not that.
The Goal
The goal was to dynamically move the laptop’s only GPU between the Linux host and the Windows guest.
Conceptually:
Before VM start:
Linux host uses the Intel GPU through xe.
When VM starts:
Stop the host display stack.
Detach the GPU from xe.
Bind it to vfio-pci.
Start the Windows 11 VM.
Let Windows use the physical Intel GPU.
When VM stops:
Shut down or destroy the VM.
Detach the GPU from vfio-pci.
Bind it back to xe.
Restart the Linux display manager.
The desired transition was:
xe
↓
vfio-pci
↓
Windows guest
↓
vfio-pci
↓
xe
Because this was a single-GPU laptop, SSH access was mandatory. Once the host display stack stops, the laptop screen can go black. In this experiment, Tailscale and SSH were the recovery path.
That saved the session more than once.
Building a Known-Good VM First
Before touching GPU passthrough, I built a normal Windows 11 VM.
The VM used:
Machine type: q35
Firmware: OVMF / UEFI Secure Boot
Disk: VirtIO
Network: VirtIO
TPM: Emulated TPM 2.0
Display: SPICE/QXL
CPU mode: host-passthrough
During Windows installation, the VirtIO disk did not appear until I loaded the driver from the virtio-win ISO. In this case, the working storage driver was viostor.
After Windows installed, I installed the VirtIO guest tools and confirmed that the VM booted normally.
This mattered. Before adding VFIO complexity, I wanted a known-good Windows guest.
The First Good Sign: IOMMU Grouping
The GPU appeared on the host as:
0000:00:02.0 VGA compatible controller:
Intel Corporation Arrow Lake-P [Arc Pro 130T/140T] [8086:7d51]
Kernel driver in use: xe
Kernel modules: i915, xe
The IOMMU grouping was favorable. The GPU was alone in its group:
/sys/kernel/iommu_groups/0/devices/0000:00:02.0
That was encouraging. If the GPU had been grouped with unrelated platform devices, the experiment would have become much less attractive.
The Second Good Sign: xe Could Detach and Reattach
Before starting the VM, I tested only the driver handoff:
xe → vfio-pci → xe
This worked.
The GPU moved from the host xe driver to vfio-pci, and then back from vfio-pci to xe.
That was one of the biggest unknowns going into the experiment. The xe driver is still relatively new compared to older Intel graphics paths, and I did not want to assume that runtime rebinding of a single active laptop GPU would work.
Kernel-level rebinding worked.
The graphical session did not always recover visually without rebooting, but the GPU itself did bind back to xe.
At this point, the project was still alive.
Adding the GPU to the VM
The Intel GPU was added to the VM as a PCI host device. The important part was that libvirt should not automatically manage the device, because a wrapper script handled the detach and reattach flow.
Conceptually, the hostdev looked like this:
<hostdev mode="subsystem" type="pci" managed="no">
<driver name="vfio"/>
<source>
<address domain="0x0000" bus="0x00" slot="0x02" function="0x0"/>
</source>
</hostdev>
The first QEMU attempt failed with a ROM-related error:
vfio-pci: Cannot read device rom at 0000:00:02.0
Device option ROM contents are probably invalid.
Skip option ROM probe with rombar=0, or load from file with romfile=
Adding this fixed that specific problem:
<rom bar="off"/>
After that, the VM started.
Windows Saw the GPU
With rombar=0, Windows booted through the QXL/SPICE fallback display.
Inside Device Manager, the passed-through Intel GPU initially appeared as:
Microsoft Basic Display Adapter
After installing Intel’s graphics driver, it became:
Intel(R) Arc(TM) Graphics
That was an important milestone.
The GPU was not invisible to the guest. Windows saw the PCI device, matched it to Intel’s driver, and installed the Intel graphics stack.
Then the real blocker appeared:
Code 43
CM_PROB_FAILED_POST_START
The Intel driver was installed, but it failed to initialize the device.
The Experiments
At this point, the work became hypothesis-driven. We tried to isolate whether the failure came from firmware exposure, guest PCI placement, CPU topology, QEMU quirks, or VM detection.
Experiment: rombar=0
Why: QEMU could not read a valid option ROM from the iGPU
Result: Fixed the QEMU ROM error
Experiment: x-igd-opregion=true
Why: Intel iGPUs depend on OpRegion for firmware/display information
Result: Accepted by QEMU, but still Code 43
Experiment: x-igd-gms=2
Why: Some Intel iGPU passthrough setups need stolen-memory related configuration
Result: Rejected by QEMU: not supported on this device
Experiment: CPU topology fix
Why: Windows saw an awkward CPU topology and the VM was slow
Result: Fixed VM responsiveness
Experiment: maxphysaddr limit=42
Why: QEMU showed a DMA mapping warning
Result: Tested as a possible fix, but still Code 43
Experiment: Guest PCI address 00:02.0
Why: Intel integrated graphics may expect the traditional iGPU address
Result: Changed device behavior, but still Code 43
Experiment: Remove ghost Intel device instances
Why: PCI address changes created stale Windows device entries
Result: Cleaned up Device Manager state
Experiment: Hide KVM / disable hypervisor flag
Why: Tested whether Intel's driver disliked an obvious VM environment
Result: Still Code 43
The two most interesting changes were CPU topology and guest PCI placement.
CPU Topology: A Real Performance Fix
The Windows VM initially felt painfully slow.
The host had 16 physical CPU threads, and the VM was configured with 10 vCPUs, but the QEMU command line revealed a bad topology:
-smp 10,sockets=10,cores=1,threads=1
Windows did not behave well with that layout.
Changing the CPU topology to one socket with ten cores made the VM much more responsive:
<cpu mode="host-passthrough" check="none" migratable="on">
<topology sockets="1" dies="1" clusters="1" cores="10" threads="1"/>
<maxphysaddr mode="passthrough" limit="42"/>
</cpu>
This did not fix the Intel GPU, but it made the debugging process much more usable.
Moving the iGPU to Guest Address 00:02.0
Initially, the GPU appeared in the guest behind a PCIe root port, effectively as something like:
06:00.0
We moved it to the traditional integrated graphics address:
00:02.0
The final hostdev conceptually became:
<hostdev mode="subsystem" type="pci" managed="no">
<driver name="vfio"/>
<source>
<address domain="0x0000" bus="0x00" slot="0x02" function="0x0"/>
</source>
<rom bar="off"/>
<address type="pci" domain="0x0000" bus="0x00" slot="0x02" function="0x0"/>
</hostdev>
QEMU then launched the device like this:
-device vfio-pci,host=0000:00:02.0,bus=pcie.0,addr=0x2,rombar=0,x-igd-opregion=true
This changed behavior slightly. Windows briefly showed multiple Intel device instances after the PCI address move. After removing ghost device instances and rebooting, it settled back to one Intel Arc Graphics device.
But the result remained:
Code 43
The Final State
By the end, the setup had reached this point:
Linux host xe driver
↓
vfio-pci
↓
QEMU hostdev assignment
↓
Windows PCI enumeration
↓
Intel graphics driver installed
↓
Intel driver fails during initialization
The final failure was not IOMMU grouping.
It was not QEMU refusing the device.
It was not Windows failing to see the PCI device.
It was Intel’s Windows graphics driver failing to initialize the passed-through Arrow Lake integrated GPU.
The final visible error was:
Intel(R) Arc(TM) Graphics
Code 43
CM_PROB_FAILED_POST_START
The laptop internal panel never lit up. That may simply be because the Intel driver never successfully initialized the device.
What We Did Not Try
We stopped before trying the more destructive or time-consuming paths:
Removing QXL/SPICE entirely
Booting with only the Intel GPU as the display device
Enabling RDP first, then removing the virtual display
Supplying a custom Intel GOP / option ROM
Trying older or newer Intel graphics drivers
Trying a Linux guest instead of Windows
Trying different QEMU or kernel builds
Waiting for newer xe / QEMU / Intel driver updates
At that point, the probability-to-effort ratio was not attractive anymore.
Was This a Misconfiguration?
The evidence suggests that the passthrough path itself functioned correctly.
The device moved from the host to vfio-pci. QEMU assigned it to the VM. Windows detected it. Intel’s driver installed. OpRegion was enabled. The guest PCI address was changed to 00:02.0.
The remaining failure appears to occur during Intel driver initialization inside the Windows guest.
That points less toward a basic VFIO mistake and more toward a compatibility boundary involving this specific combination:
Arrow Lake integrated Intel Arc GPU
Laptop firmware/display path
Linux xe driver
QEMU/KVM passthrough
Windows Intel graphics driver
That does not mean it is impossible forever.
It means this specific stack did not work for us at the time of testing.
How It Started
Maybe we can do single-GPU passthrough on this laptop.
How It Went
The GPU detached from xe.
It bound to vfio-pci.
QEMU assigned it.
Windows saw it.
Intel’s driver installed.
OpRegion worked.
Guest 00:02.0 worked.
The driver still ended at Code 43.
How It Is Going
We stopped.
Not because nothing worked, but because enough worked to show that the remaining problem was probably not basic configuration anymore.
That is the useful part of this failure.
We did not learn that it simply does not work.
We learned where it stops working.
Conclusion
This did not become a working VFIO setup.
But it did become a useful failure report.
On this machine, with this software stack:
Intel Core Ultra 9 285H
Arrow Lake-P Intel Arc graphics
Linux xe driver
QEMU/KVM/libvirt
Windows 11 guest
we were able to pass the GPU far enough that Windows recognized it and installed the Intel graphics driver.
The blocker was Intel’s Windows driver failing to initialize the passed-through integrated GPU with Code 43.
That is still a failure.
But it is a much better failure than where we started.
Appendix: Exact Scripts and Final XML

Before the Intel driver installation — 1

Before the Intel driver installation — 2

After the Intel driver installation
vfio-vm script:
[embed]vfio-vm.sh Edit descriptiondrive.google.com
qemu xml file:
[embed]w11dump.xml Edit descriptiondrive.google.com
lspci:
0000:00:00.0 Host bridge: Intel Corporation Arrow Lake-H 6p+8e cores Host Bridge/DRAM Controller (rev 05)
0000:00:02.0 VGA compatible controller: Intel Corporation Arrow Lake-P [Arc Pro 130T/140T] (rev 03)
0000:00:04.0 Signal processing controller: Intel Corporation Meteor Lake-P Dynamic Tuning Technology (rev 05)
0000:00:07.0 PCI bridge: Intel Corporation Meteor Lake-P Thunderbolt 4 PCI Express Root Port #0 (rev 10)
0000:00:07.1 PCI bridge: Intel Corporation Meteor Lake-P Thunderbolt 4 PCI Express Root Port #1 (rev 10)
0000:00:08.0 System peripheral: Intel Corporation Arrow Lake Gaussian & Neural Accelerator
0000:00:0a.0 Signal processing controller: Intel Corporation Meteor Lake-P Platform Monitoring Technology (rev 01)
0000:00:0b.0 Processing accelerators: Intel Corporation Meteor Lake NPU (rev 05)
0000:00:0d.0 USB controller: Intel Corporation Meteor Lake-P Thunderbolt 4 USB Controller (rev 10)
0000:00:0d.2 USB controller: Intel Corporation Meteor Lake-P Thunderbolt 4 NHI #0 (rev 10)
0000:00:0e.0 RAID bus controller: Intel Corporation Volume Management Device NVMe RAID Controller Intel Corporation
0000:00:12.0 Serial controller: Intel Corporation Arrow Lake Integrated Sensor Hub
0000:00:14.0 USB controller: Intel Corporation Arrow Lake USB 3.2 xHCI Controller
0000:00:14.2 RAM memory: Intel Corporation Arrow Lake Shared SRAM
0000:00:14.3 Network controller: Intel Corporation Arrow Lake CNVi WiFi
0000:00:15.0 Serial bus controller: Intel Corporation Arrow Lake-H [Serial IO I2C Host Controller]
0000:00:15.1 Serial bus controller: Intel Corporation Arrow Lake-H [Serial IO I2C Host Controller]
0000:00:16.0 Communication controller: Intel Corporation Arrow Lake HECI Controller #1
0000:00:1e.0 Communication controller: Intel Corporation Arrow Lake-H [PCH Serial IO UART Host Controller]
0000:00:1e.3 Serial bus controller: Intel Corporation Arrow Lake-H [LPC/eSPI Controller]
0000:00:1f.0 ISA bridge: Intel Corporation Arrow Lake-H eSPI Controller
0000:00:1f.3 Multimedia audio controller: Intel Corporation Arrow Lake cAVS
0000:00:1f.4 SMBus: Intel Corporation Arrow Lake SMBus Controller
0000:00:1f.5 Serial bus controller: Intel Corporation Arrow Lake SPI Controller
10000:e0:06.0 System peripheral: Intel Corporation RST VMD Managed Controller
10000:e0:06.2 PCI bridge: Intel Corporation Arrow Lake-H/U PCIe Root Port #11 (PXPE) (rev 10)
10000:e1:00.0 Non-Volatile memory controller: Micron Technology Inc 2500 NVMe SSD (DRAM-less) (rev 01) 메타데이터
- post_id
- 7ac5148ae375
- slug
- a-failure-report-single-gpu-passthrough-on-arrow-lake-with-the-xe-driver-7ac5148ae375
- url
- https://medium.com/@tunahanyrd/a-failure-report-single-gpu-passthrough-on-arrow-lake-with-the-xe-driver-7ac5148ae375
- canonical_url
- https://medium.com/@tunahanyrd/a-failure-report-single-gpu-passthrough-on-arrow-lake-with-the-xe-driver-7ac5148ae375
- author_url
- https://medium.com/@tunahanyrd
- status
- ok
- fetched_at
- 2026-07-19 15:11:09