Skip to content

kubevirt: pin Flatcar VMs to PCI root complex to preserve Ignition#2057

Open
mihiragrawal wants to merge 1 commit into
kubermatic:mainfrom
mihiragrawal:main
Open

kubevirt: pin Flatcar VMs to PCI root complex to preserve Ignition#2057
mihiragrawal wants to merge 1 commit into
kubermatic:mainfrom
mihiragrawal:main

Conversation

@mihiragrawal

Copy link
Copy Markdown

What this PR does / why we need it:

On KubeVirt 1.6.4 and newer, Flatcar worker VMs boot but never receive their Ignition configuration, so the node never joins the cluster. KubeVirt's PCIe-hotplug port reservation re-defines the libvirt domain a second time, and that path runs an XML round-trip that cannot preserve the qemu namespace — dropping the <qemu:commandline> -fw_cfg opt/com.coreos/config argument that carries Flatcar's stage-1 Ignition. This PR sets the kubevirt.io/placePCIDevicesOnRootComplex annotation on Flatcar VMs, which makes KubeVirt skip the extra hotplug ports and the second domain define, so the fw_cfg argument survives. cloud-init based OSes (e.g. Ubuntu) are unaffected because they are delivered as a disk rather than a qemu command-line argument.

Which issue(s) this PR fixes:

Fixes #

None (root cause is upstream KubeVirt — see Special notes)

What type of PR is this?

Special notes for your reviewer:

  • Root cause is an upstream KubeVirt defect, not machine-controller: an xml.Unmarshal round-trip in ApplySidecarHooks silently drops the qemu-namespaced command line, which became fatal once KubeVirt 1.6.4 added a second domain define in the PCIe-hotplug port path. Upstream refs: [sidecars] XML round-trip via xml.Unmarshal/xml.Marshal drops or corrupts namespace-scoped domain sections (qemu:commandline/qemu:arg) kubevirt/kubevirt#16901 (root cause), sidecar hooks: preserve QEMUCmd across XML round-trip kubevirt/kubevirt#18460 (fix, still open, no release-1.6 backport yet). This PR is the workaround until that fix ships in the KubeVirt version we deploy.
  • Scoped to Flatcar deliberately, to avoid changing behaviour for other operating systems. It is applied unconditionally for Flatcar (not gated on the KubeVirt version) because the annotation is harmless on unaffected versions — it only disables extra PCIe hotplug ports, and worker VMs never hotplug PCI devices.
  • Users can still override it per-pool via spec.template.metadata.annotations on the MachineDeployment, since machine-controller merges those after this default.
  • No testdata fixture currently exercises Flatcar (none set kubevirt.io/ignitiondata), so no golden files change. Happy to add a Flatcar fixture + case if you'd like the path covered.

Does this PR introduce a user-facing change? Then add your Release Note here:

Fix Flatcar-based KubeVirt machines failing to bootstrap on KubeVirt 1.6.4 and newer by setting the kubevirt.io/placePCIDevicesOnRootComplex annotation, which preserves the Ignition (fw_cfg) configuration.

Documentation:

NONE

On KubeVirt >= 1.6.4, Flatcar worker VMs boot without their Ignition
configuration and never join the cluster. KubeVirt's PCIe-hotplug port
reservation re-defines the libvirt domain a second time; that path runs
an XML round-trip that cannot preserve the qemu namespace, so it drops
the <qemu:commandline> "-fw_cfg opt/com.coreos/config" argument that
carries Flatcar's stage-1 Ignition. cloud-init (Ubuntu, noCloud) is
unaffected because it is delivered as a disk, not a qemu command-line arg.

Setting the kubevirt.io/placePCIDevicesOnRootComplex annotation makes
KubeVirt skip the extra hotplug ports and the second domain define, so
the fw_cfg argument survives. Worker VMs never hotplug PCI devices, so
the lost hotplug capacity has no practical impact. Scoped to Flatcar to
avoid changing behaviour for other operating systems.
Workaround; remove once the upstream fix is in the deployed KubeVirt.
Refs: kubevirt/kubevirt#16901 (root cause), kubevirt/kubevirt#18460 (fix)
@kubermatic-bot kubermatic-bot added release-note Denotes a PR that will be considered when it comes time to generate release notes. docs/none Denotes a PR that doesn't need documentation (changes). dco-signoff: yes Denotes that all commits in the pull request have the valid DCO signoff message. labels Jul 23, 2026
@kubermatic-bot

Copy link
Copy Markdown
Contributor

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by:
Once this PR has been reviewed and has the lgtm label, please assign buraksekili for approval. For more information see the Code Review Process.

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@kubermatic-bot kubermatic-bot added the size/XS Denotes a PR that changes 0-9 lines, ignoring generated files. label Jul 23, 2026
@mihiragrawal
mihiragrawal requested a review from moadqassem July 23, 2026 05:58
@mihiragrawal mihiragrawal self-assigned this Jul 23, 2026
mihiragrawal added a commit to mihiragrawal/docs that referenced this pull request Jul 23, 2026
Document the KubeVirt >= 1.6.4 regression that drops the fw_cfg
(opt/com.coreos/config) qemu argument for Flatcar VMs, so Flatcar
worker nodes never receive their Ignition config and fail to join the
user cluster. Ubuntu (cloud-init/noCloud) is unaffected.

The page covers the problem, root cause, the machine-controller
workaround (the kubevirt.io/placePCIDevicesOnRootComplex annotation,
kubermatic/machine-controller#2057) plus a manual MachineDeployment
fallback, the Flatcar-only scope, the trade-off (disables unused PCIe
hotplug on worker VMs), and upstream references
(kubevirt/kubevirt#16901, kubevirt/kubevirt#18460).
@mihiragrawal

Copy link
Copy Markdown
Author

/retest

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

Labels

dco-signoff: yes Denotes that all commits in the pull request have the valid DCO signoff message. docs/none Denotes a PR that doesn't need documentation (changes). release-note Denotes a PR that will be considered when it comes time to generate release notes. size/XS Denotes a PR that changes 0-9 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants