virtio-devices: Fix cap_len for VIRTIO_PCI_CAP_PCI_CFG

VirtioPciCfgCap::new built its inner header via VirtioPciCap::new,
which sized cap_len from the bare virtio_pci_cap layout, yielding
16. The emitted capability is VirtioPciCfgCap, which appends a four
byte pci_cfg_data window, so the correct value is 20.

The virtio 1.2 specification defines this cap as virtio_pci_cap
followed by pci_cfg_data[4] and requires cap_len to
cover the whole structure. Build the header inline so cap_len
reflects the actual emitted size, matching VirtioPciNotifyCap and
VirtioPciCap64.

Signed-off-by: Anatol Belski <anbelski@linux.microsoft.com>
This commit is contained in:
Anatol Belski
2026-05-16 15:41:16 +02:00
committed by Rob Bradford
parent 547a78999e
commit b4dea599a3

View File

@@ -9,6 +9,7 @@
use std::any::Any;
use std::cmp;
use std::io::Write;
use std::mem::size_of;
use std::ops::Deref;
use std::sync::atomic::{AtomicBool, AtomicU8, AtomicU16, AtomicUsize, Ordering};
use std::sync::{Arc, Barrier, Mutex};
@@ -208,7 +209,15 @@ impl PciCapability for VirtioPciCfgCap {
impl VirtioPciCfgCap {
fn new() -> Self {
VirtioPciCfgCap {
cap: VirtioPciCap::new(PciCapabilityType::Pci, 0, 0, 0),
cap: VirtioPciCap {
cap_len: (size_of::<VirtioPciCfgCap>() as u8) + VIRTIO_PCI_CAP_LEN_OFFSET,
cfg_type: PciCapabilityType::Pci as u8,
pci_bar: 0,
id: 0,
padding: [0; 2],
offset: Le32::from(0),
length: Le32::from(0),
},
..Default::default()
}
}