]> git.ipfire.org Git - thirdparty/linux.git/commitdiff
vfio/pci: Expose latched module parameter policy in debugfs
authorAlex Williamson <alex.williamson@nvidia.com>
Mon, 15 Jun 2026 19:12:34 +0000 (13:12 -0600)
committerAlex Williamson <alex@shazbot.org>
Mon, 29 Jun 2026 20:26:31 +0000 (14:26 -0600)
The nointxmask and disable_idle_d3 module parameters remain writable,
but vfio-pci now latches their values into each device at init.  Once a
device is registered, changing the module parameter only affects future
devices, leaving no direct way to confirm the effective policy for an
existing device.

Add a pci debugfs directory under the VFIO device debugfs root and
report the per-device nointxmask and disable_idle_d3 values.  These are
read-only debugfs views and use the same Y/N bool output convention as
the module parameters.

Read-only vfio-pci parameters, such as disable_vga, are not exposed here
because they cannot drift from the latched device value, therefore the
existing module parameter exposure via sysfs is sufficient.

Note that while only vfio-pci currently provides these options, the
implementation is in vfio-pci-core and therefore properly reflects the
device policy in the core, regardless of driver.

Assisted-by: OpenAI Codex:gpt-5
Cc: Guixin Liu <kanie@linux.alibaba.com>
Signed-off-by: Alex Williamson <alex.williamson@nvidia.com>
Reviewed-by: Kevin Tian <kevin.tian@intel.com>
Link: https://lore.kernel.org/r/20260615191241.688297-7-alex.williamson@nvidia.com
Signed-off-by: Alex Williamson <alex@shazbot.org>
Documentation/ABI/testing/debugfs-vfio
drivers/vfio/pci/vfio_pci_core.c

index 70ec2d454686290e13380340dfd6a5a67a642533..ed2f29c3a9b41588198dce1546f3cd702b3a30da 100644 (file)
@@ -29,3 +29,29 @@ Date:                Oct 2025
 KernelVersion: 6.18
 Contact:       Cédric Le Goater <clg@redhat.com>
 Description:   Read the migration features of the vfio device.
+
+What:          /sys/kernel/debug/vfio/<device>/pci
+Date:          June 2026
+KernelVersion: 7.2
+Contact:       Alex Williamson <alex.williamson@nvidia.com>
+Description:   This debugfs file directory is used for debugging
+               VFIO PCI devices.
+
+What:          /sys/kernel/debug/vfio/<device>/pci/nointxmask
+Date:          June 2026
+KernelVersion: 7.2
+Contact:       Alex Williamson <alex.williamson@nvidia.com>
+Description:   Read the nointxmask policy latched for this device.  This
+               policy governs whether the device may use PCI 2.3 style
+               INTx masking when supported, reporting a value of "N", or
+               requires APIC level INTx masking, reporting a value of "Y".
+
+What:          /sys/kernel/debug/vfio/<device>/pci/disable_idle_d3
+Date:          June 2026
+KernelVersion: 7.2
+Contact:       Alex Williamson <alex.williamson@nvidia.com>
+Description:   Read the disable_idle_d3 policy latched for this device.  This
+               policy governs whether the device PM runtime usage count is
+               kept elevated while the device is bound to the driver and
+               unused, reporting a value of "Y", or decremented to allow the
+               device to enter a low power state, reporting a value of "N".
index db36d903dcd40e75e7a499f3ee93cf3dba05cc6c..3f11a9624b9c036f332463b320bb54ac08bf3163 100644 (file)
@@ -11,6 +11,7 @@
 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
 
 #include <linux/aperture.h>
+#include <linux/debugfs.h>
 #include <linux/device.h>
 #include <linux/eventfd.h>
 #include <linux/file.h>
@@ -29,6 +30,7 @@
 #include <linux/sched/mm.h>
 #include <linux/iommufd.h>
 #include <linux/pci-p2pdma.h>
+#include <linux/seq_file.h>
 #if IS_ENABLED(CONFIG_EEH)
 #include <asm/eeh.h>
 #endif
@@ -97,6 +99,60 @@ static inline bool vfio_vga_disabled(struct vfio_pci_core_device *vdev)
 #endif
 }
 
+#ifdef CONFIG_VFIO_DEBUGFS
+static struct vfio_pci_core_device *
+vfio_pci_core_debugfs_private(struct seq_file *seq)
+{
+       struct device *dev = seq->private;
+       struct vfio_device *core_vdev = container_of(dev, struct vfio_device,
+                                                    device);
+
+       return container_of(core_vdev, struct vfio_pci_core_device, vdev);
+}
+
+static int vfio_pci_core_debugfs_nointxmask(struct seq_file *seq, void *data)
+{
+       struct vfio_pci_core_device *vdev = vfio_pci_core_debugfs_private(seq);
+
+       seq_puts(seq, vdev->nointxmask ? "Y\n" : "N\n");
+       return 0;
+}
+
+static int vfio_pci_core_debugfs_disable_idle_d3(struct seq_file *seq,
+                                                void *data)
+{
+       struct vfio_pci_core_device *vdev = vfio_pci_core_debugfs_private(seq);
+
+       seq_puts(seq, vdev->disable_idle_d3 ? "Y\n" : "N\n");
+       return 0;
+}
+
+/*
+ * disable_idle_d3 and nointxmask are writable module parameters latched
+ * per device at init, so a device's effective value can differ from the
+ * current parameter setting.  Expose the per-device (read-only) values
+ * here for visibility; read-only parameters can't drift and are omitted.
+ */
+static void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
+{
+       struct device *dev = &vdev->vdev.device;
+       struct dentry *pci_dir;
+
+       if (IS_ERR_OR_NULL(vdev->vdev.debug_root))
+               return;
+
+       pci_dir = debugfs_create_dir("pci", vdev->vdev.debug_root);
+       debugfs_create_devm_seqfile(dev, "nointxmask", pci_dir,
+                                   vfio_pci_core_debugfs_nointxmask);
+       debugfs_create_devm_seqfile(dev, "disable_idle_d3", pci_dir,
+                                   vfio_pci_core_debugfs_disable_idle_d3);
+}
+#else
+static inline void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
+{
+}
+#endif /* CONFIG_VFIO_DEBUGFS */
+
 /*
  * Our VGA arbiter participation is limited since we don't know anything
  * about the device itself.  However, if the device is the only VGA device
@@ -2242,6 +2298,9 @@ int vfio_pci_core_register_device(struct vfio_pci_core_device *vdev)
        ret = vfio_register_group_dev(&vdev->vdev);
        if (ret)
                goto out_power;
+
+       vfio_pci_core_debugfs_init(vdev);
+
        return 0;
 
 out_power: