* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-22 7:18 [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2) Dave Airlie
@ 2026-09-22 7:25 ` sashiko-bot
2026-09-22 8:44 ` Jani Nikula
` (4 subsequent siblings)
5 siblings, 0 replies; 8+ messages in thread
From: sashiko-bot @ 2026-09-22 7:25 UTC (permalink / raw)
To: Dave Airlie; +Cc: dri-devel, kvm, linux-pci
> From: Dave Airlie <airlied@redhat.com>
>
> This changes the vgaarb client API so that the user can pass a
> private data pointer into the register that will get used in
> the decode callback.
>
> This allows a bunch of pdev conversions in the drivers, and lets
> some future vfio cleanups be nicer.
>
> I'd like to merge this via the drm next tree but also fine with
> it going via pci.
>
> Signed-off-by: Dave Airlie <airlied@redhat.com>
Sashiko has reviewed this patch and found no issues. It looks great!
--
Sashiko AI review · https://sashiko.dev/#/patchset/20260922071807.2533884-1-airlied@gmail.com?part=1
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-22 7:18 [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2) Dave Airlie
2026-09-22 7:25 ` sashiko-bot
@ 2026-09-22 8:44 ` Jani Nikula
2026-09-22 15:05 ` Alex Deucher
` (3 subsequent siblings)
5 siblings, 0 replies; 8+ messages in thread
From: Jani Nikula @ 2026-09-22 8:44 UTC (permalink / raw)
To: Dave Airlie, dri-devel, linux-pci, kvm
Cc: Jason Gunthorpe, Dave Airlie, Alex Williamson, Bjorn Helgaas,
Rodrigo Vivi, Alex Deucher
On Tue, 22 Sep 2026, Dave Airlie <airlied@gmail.com> wrote:
> From: Dave Airlie <airlied@redhat.com>
>
> This changes the vgaarb client API so that the user can pass a
> private data pointer into the register that will get used in
> the decode callback.
>
> This allows a bunch of pdev conversions in the drivers, and lets
> some future vfio cleanups be nicer.
>
> I'd like to merge this via the drm next tree but also fine with
> it going via pci.
>
> Signed-off-by: Dave Airlie <airlied@redhat.com>
> Cc: Alex Williamson <alex@shazbot.org>
> Cc: Bjorn Helgaas <bhelgaas@google.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: Alex Deucher <alexander.deucher@amd.com>
> ---
> v2: fix loongson (spotted by sashiko)
> ---
> drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 +++---
> drivers/gpu/drm/i915/display/intel_vga.c | 7 ++++---
> drivers/gpu/drm/loongson/lsdc_drv.c | 4 ++--
> drivers/gpu/drm/nouveau/nouveau_vga.c | 6 +++---
> drivers/gpu/drm/radeon/radeon_device.c | 7 +++----
> drivers/pci/vgaarb.c | 13 +++++++++----
> drivers/vfio/pci/vfio_pci_core.c | 9 +++++----
> include/linux/vgaarb.h | 8 +++++---
> 8 files changed, 34 insertions(+), 26 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> index 62b5b4a23f17..1344b2b1bd16 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> @@ -1435,10 +1435,10 @@ bool amdgpu_device_should_use_aspm(struct amdgpu_device *adev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int amdgpu_device_vga_set_decode(struct pci_dev *pdev,
> +static unsigned int amdgpu_device_vga_set_decode(void *data,
> bool state)
> {
> - struct amdgpu_device *adev = drm_to_adev(pci_get_drvdata(pdev));
> + struct amdgpu_device *adev = (struct amdgpu_device *)data;
The cast is superfluous. Ditto everywhere else.
Other than that,
Reviewed-by: Jani Nikula <jani.nikula@intel.com>
>
> amdgpu_asic_set_vga_state(adev, state);
> if (state)
> @@ -4208,7 +4208,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,
> * ignore it
> */
> if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)
> - vga_client_register(adev->pdev, amdgpu_device_vga_set_decode);
> + vga_client_register(adev->pdev, amdgpu_device_vga_set_decode, adev);
>
> px = amdgpu_device_supports_px(adev);
>
> diff --git a/drivers/gpu/drm/i915/display/intel_vga.c b/drivers/gpu/drm/i915/display/intel_vga.c
> index 4966fd7eea92..0889edb36190 100644
> --- a/drivers/gpu/drm/i915/display/intel_vga.c
> +++ b/drivers/gpu/drm/i915/display/intel_vga.c
> @@ -283,9 +283,10 @@ void intel_vga_disable(struct intel_display *display)
> intel_de_posting_read(display, vga_reg);
> }
>
> -static unsigned int intel_vga_set_decode(struct pci_dev *pdev, bool enable_decode)
> +static unsigned int intel_vga_set_decode(void *data, bool enable_decode)
> {
> - struct intel_display *display = to_intel_display(pdev);
> + struct intel_display *display = (struct intel_display *)data;
> + struct pci_dev *pdev = to_pci_dev(display->drm->dev);
> unsigned int decodes = VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
>
> drm_dbg_kms(display->drm, "%s VGA decode due to VGA arbitration\n",
> @@ -331,7 +332,7 @@ void intel_vga_register(struct intel_display *display)
> * then we do not take part in VGA arbitration and the
> * vga_client_register() fails with -ENODEV.
> */
> - ret = vga_client_register(pdev, intel_vga_set_decode);
> + ret = vga_client_register(pdev, intel_vga_set_decode, display);
> drm_WARN_ON(display->drm, ret && ret != -ENODEV);
> }
>
> diff --git a/drivers/gpu/drm/loongson/lsdc_drv.c b/drivers/gpu/drm/loongson/lsdc_drv.c
> index 3fd828d23271..5a13df31eb90 100644
> --- a/drivers/gpu/drm/loongson/lsdc_drv.c
> +++ b/drivers/gpu/drm/loongson/lsdc_drv.c
> @@ -254,7 +254,7 @@ lsdc_create_device(struct pci_dev *pdev,
>
> /* For multiple GPU driver instance co-exixt in the system */
>
> -static unsigned int lsdc_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int lsdc_vga_set_decode(void *data, bool state)
> {
> return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
> }
> @@ -291,7 +291,7 @@ static int lsdc_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
>
> pci_set_drvdata(pdev, ddev);
>
> - vga_client_register(pdev, lsdc_vga_set_decode);
> + vga_client_register(pdev, lsdc_vga_set_decode, NULL);
>
> drmm_kms_helper_poll_init(ddev);
>
> diff --git a/drivers/gpu/drm/nouveau/nouveau_vga.c b/drivers/gpu/drm/nouveau/nouveau_vga.c
> index 29a801124e56..6662e30466f2 100644
> --- a/drivers/gpu/drm/nouveau/nouveau_vga.c
> +++ b/drivers/gpu/drm/nouveau/nouveau_vga.c
> @@ -9,9 +9,9 @@
> #include "nouveau_vga.h"
>
> static unsigned int
> -nouveau_vga_set_decode(struct pci_dev *pdev, bool state)
> +nouveau_vga_set_decode(void *data, bool state)
> {
> - struct nouveau_drm *drm = pci_get_drvdata(pdev);
> + struct nouveau_drm *drm = (struct nouveau_drm *)data;
> struct nvif_object *device = &drm->client.device.object;
>
> if (drm->client.device.info.family == NV_DEVICE_INFO_V0_CURIE &&
> @@ -103,7 +103,7 @@ nouveau_vga_init(struct nouveau_drm *drm)
> return;
> pdev = to_pci_dev(dev->dev);
>
> - vga_client_register(pdev, nouveau_vga_set_decode);
> + vga_client_register(pdev, nouveau_vga_set_decode, drm);
>
> /* don't register Thunderbolt eGPU with vga_switcheroo */
> if (pci_is_thunderbolt_attached(pdev))
> diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
> index 9523240110a6..cf8a6bd00c77 100644
> --- a/drivers/gpu/drm/radeon/radeon_device.c
> +++ b/drivers/gpu/drm/radeon/radeon_device.c
> @@ -1076,10 +1076,9 @@ void radeon_combios_fini(struct radeon_device *rdev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int radeon_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int radeon_vga_set_decode(void *data, bool state)
> {
> - struct drm_device *dev = pci_get_drvdata(pdev);
> - struct radeon_device *rdev = dev->dev_private;
> + struct radeon_device *rdev = (struct radeon_device *)data;
> radeon_vga_set_state(rdev, state);
> if (state)
> return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM |
> @@ -1431,7 +1430,7 @@ int radeon_device_init(struct radeon_device *rdev,
> /* if we have > 1 VGA cards, then disable the radeon VGA resources */
> /* this will fail for cards that aren't VGA class devices, just
> * ignore it */
> - vga_client_register(rdev->pdev, radeon_vga_set_decode);
> + vga_client_register(rdev->pdev, radeon_vga_set_decode, rdev);
>
> if (rdev->flags & RADEON_IS_PX)
> runtime = true;
> diff --git a/drivers/pci/vgaarb.c b/drivers/pci/vgaarb.c
> index 3de05aee7859..3e58b2c05c85 100644
> --- a/drivers/pci/vgaarb.c
> +++ b/drivers/pci/vgaarb.c
> @@ -51,7 +51,8 @@ struct vga_device {
> unsigned int mem_norm_cnt; /* normal MEM count */
> bool bridge_has_one_vga;
> bool is_firmware_default; /* device selected by firmware */
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode);
> + unsigned int (*set_decode)(void *data, bool decode);
> + void *set_decode_data;
> };
>
> static LIST_HEAD(vga_list);
> @@ -935,6 +936,7 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * vga_client_register - register or unregister a VGA arbitration client
> * @pdev: PCI device of the VGA client
> * @set_decode: VGA decode change callback
> + * @data: private data to pass to callback
> *
> * Clients have two callback mechanisms they can use.
> *
> @@ -956,15 +958,18 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * Returns: 0 on success, -ENODEV on failure
> */
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode))
> + unsigned int (*set_decode)(void *data, bool decode),
> + void *data)
> {
> unsigned long flags;
> struct vga_device *vgadev;
>
> spin_lock_irqsave(&vga_lock, flags);
> vgadev = vgadev_find(pdev);
> - if (vgadev)
> + if (vgadev) {
> vgadev->set_decode = set_decode;
> + vgadev->set_decode_data = data;
> + }
> spin_unlock_irqrestore(&vga_lock, flags);
> if (!vgadev)
> return -ENODEV;
> @@ -1464,7 +1469,7 @@ static void vga_arbiter_notify_clients(void)
> spin_lock_irqsave(&vga_lock, flags);
> list_for_each_entry(vgadev, &vga_list, list) {
> if (vgadev->set_decode) {
> - new_decodes = vgadev->set_decode(vgadev->pdev,
> + new_decodes = vgadev->set_decode(vgadev->set_decode_data,
> new_state);
> vga_update_device_decodes(vgadev, new_decodes);
> }
> diff --git a/drivers/vfio/pci/vfio_pci_core.c b/drivers/vfio/pci/vfio_pci_core.c
> index 6757054e9d87..b04ce3ded08c 100644
> --- a/drivers/vfio/pci/vfio_pci_core.c
> +++ b/drivers/vfio/pci/vfio_pci_core.c
> @@ -162,9 +162,10 @@ static inline void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
> * has no way to get to it and routing can be disabled externally at the
> * bridge.
> */
> -static unsigned int vfio_pci_set_decode(struct pci_dev *pdev, bool single_vga)
> +static unsigned int vfio_pci_set_decode(void *data, bool single_vga)
> {
> - struct vfio_pci_core_device *vdev = dev_get_drvdata(&pdev->dev);
> + struct vfio_pci_core_device *vdev = data;
> + struct pci_dev *pdev = vdev->pdev;
> struct pci_dev *tmp = NULL;
> unsigned char max_busnr;
> unsigned int decodes;
> @@ -2159,10 +2160,10 @@ static int vfio_pci_vga_init(struct vfio_pci_core_device *vdev)
> if (ret)
> return ret;
>
> - ret = vga_client_register(pdev, vfio_pci_set_decode);
> + ret = vga_client_register(pdev, vfio_pci_set_decode, vdev);
> if (ret)
> return ret;
> - vga_set_legacy_decoding(pdev, vfio_pci_set_decode(pdev, false));
> + vga_set_legacy_decoding(pdev, vfio_pci_set_decode(vdev, false));
> return 0;
> }
>
> diff --git a/include/linux/vgaarb.h b/include/linux/vgaarb.h
> index 97129a1bbb7d..71a364669eaf 100644
> --- a/include/linux/vgaarb.h
> +++ b/include/linux/vgaarb.h
> @@ -33,7 +33,8 @@ struct pci_dev *vga_default_device(void);
> void vga_set_default_device(struct pci_dev *pdev);
> int vga_remove_vgacon(struct pci_dev *pdev);
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state));
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data);
> #else /* CONFIG_VGA_ARB */
> static inline void vga_set_legacy_decoding(struct pci_dev *pdev,
> unsigned int decodes)
> @@ -59,7 +60,8 @@ static inline int vga_remove_vgacon(struct pci_dev *pdev)
> return 0;
> }
> static inline int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state))
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data)
> {
> return 0;
> }
> @@ -97,7 +99,7 @@ static inline int vga_get_uninterruptible(struct pci_dev *pdev,
>
> static inline void vga_client_unregister(struct pci_dev *pdev)
> {
> - vga_client_register(pdev, NULL);
> + vga_client_register(pdev, NULL, NULL);
> }
>
> #endif /* LINUX_VGA_H */
--
Jani Nikula, Intel
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-22 7:18 [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2) Dave Airlie
2026-09-22 7:25 ` sashiko-bot
2026-09-22 8:44 ` Jani Nikula
@ 2026-09-22 15:05 ` Alex Deucher
2026-09-28 19:33 ` Dave Airlie
` (2 subsequent siblings)
5 siblings, 0 replies; 8+ messages in thread
From: Alex Deucher @ 2026-09-22 15:05 UTC (permalink / raw)
To: Dave Airlie
Cc: dri-devel, linux-pci, kvm, Jason Gunthorpe, Dave Airlie,
Alex Williamson, Bjorn Helgaas, Rodrigo Vivi, Alex Deucher
On Tue, Sep 22, 2026 at 3:18 AM Dave Airlie <airlied@gmail.com> wrote:
>
> From: Dave Airlie <airlied@redhat.com>
>
> This changes the vgaarb client API so that the user can pass a
> private data pointer into the register that will get used in
> the decode callback.
>
> This allows a bunch of pdev conversions in the drivers, and lets
> some future vfio cleanups be nicer.
>
> I'd like to merge this via the drm next tree but also fine with
> it going via pci.
>
> Signed-off-by: Dave Airlie <airlied@redhat.com>
> Cc: Alex Williamson <alex@shazbot.org>
> Cc: Bjorn Helgaas <bhelgaas@google.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: Alex Deucher <alexander.deucher@amd.com>
Reviewed-by: Alex Deucher <alexander.deucher@amd.com>
> ---
> v2: fix loongson (spotted by sashiko)
> ---
> drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 +++---
> drivers/gpu/drm/i915/display/intel_vga.c | 7 ++++---
> drivers/gpu/drm/loongson/lsdc_drv.c | 4 ++--
> drivers/gpu/drm/nouveau/nouveau_vga.c | 6 +++---
> drivers/gpu/drm/radeon/radeon_device.c | 7 +++----
> drivers/pci/vgaarb.c | 13 +++++++++----
> drivers/vfio/pci/vfio_pci_core.c | 9 +++++----
> include/linux/vgaarb.h | 8 +++++---
> 8 files changed, 34 insertions(+), 26 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> index 62b5b4a23f17..1344b2b1bd16 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> @@ -1435,10 +1435,10 @@ bool amdgpu_device_should_use_aspm(struct amdgpu_device *adev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int amdgpu_device_vga_set_decode(struct pci_dev *pdev,
> +static unsigned int amdgpu_device_vga_set_decode(void *data,
> bool state)
> {
> - struct amdgpu_device *adev = drm_to_adev(pci_get_drvdata(pdev));
> + struct amdgpu_device *adev = (struct amdgpu_device *)data;
>
> amdgpu_asic_set_vga_state(adev, state);
> if (state)
> @@ -4208,7 +4208,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,
> * ignore it
> */
> if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)
> - vga_client_register(adev->pdev, amdgpu_device_vga_set_decode);
> + vga_client_register(adev->pdev, amdgpu_device_vga_set_decode, adev);
>
> px = amdgpu_device_supports_px(adev);
>
> diff --git a/drivers/gpu/drm/i915/display/intel_vga.c b/drivers/gpu/drm/i915/display/intel_vga.c
> index 4966fd7eea92..0889edb36190 100644
> --- a/drivers/gpu/drm/i915/display/intel_vga.c
> +++ b/drivers/gpu/drm/i915/display/intel_vga.c
> @@ -283,9 +283,10 @@ void intel_vga_disable(struct intel_display *display)
> intel_de_posting_read(display, vga_reg);
> }
>
> -static unsigned int intel_vga_set_decode(struct pci_dev *pdev, bool enable_decode)
> +static unsigned int intel_vga_set_decode(void *data, bool enable_decode)
> {
> - struct intel_display *display = to_intel_display(pdev);
> + struct intel_display *display = (struct intel_display *)data;
> + struct pci_dev *pdev = to_pci_dev(display->drm->dev);
> unsigned int decodes = VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
>
> drm_dbg_kms(display->drm, "%s VGA decode due to VGA arbitration\n",
> @@ -331,7 +332,7 @@ void intel_vga_register(struct intel_display *display)
> * then we do not take part in VGA arbitration and the
> * vga_client_register() fails with -ENODEV.
> */
> - ret = vga_client_register(pdev, intel_vga_set_decode);
> + ret = vga_client_register(pdev, intel_vga_set_decode, display);
> drm_WARN_ON(display->drm, ret && ret != -ENODEV);
> }
>
> diff --git a/drivers/gpu/drm/loongson/lsdc_drv.c b/drivers/gpu/drm/loongson/lsdc_drv.c
> index 3fd828d23271..5a13df31eb90 100644
> --- a/drivers/gpu/drm/loongson/lsdc_drv.c
> +++ b/drivers/gpu/drm/loongson/lsdc_drv.c
> @@ -254,7 +254,7 @@ lsdc_create_device(struct pci_dev *pdev,
>
> /* For multiple GPU driver instance co-exixt in the system */
>
> -static unsigned int lsdc_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int lsdc_vga_set_decode(void *data, bool state)
> {
> return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
> }
> @@ -291,7 +291,7 @@ static int lsdc_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
>
> pci_set_drvdata(pdev, ddev);
>
> - vga_client_register(pdev, lsdc_vga_set_decode);
> + vga_client_register(pdev, lsdc_vga_set_decode, NULL);
>
> drmm_kms_helper_poll_init(ddev);
>
> diff --git a/drivers/gpu/drm/nouveau/nouveau_vga.c b/drivers/gpu/drm/nouveau/nouveau_vga.c
> index 29a801124e56..6662e30466f2 100644
> --- a/drivers/gpu/drm/nouveau/nouveau_vga.c
> +++ b/drivers/gpu/drm/nouveau/nouveau_vga.c
> @@ -9,9 +9,9 @@
> #include "nouveau_vga.h"
>
> static unsigned int
> -nouveau_vga_set_decode(struct pci_dev *pdev, bool state)
> +nouveau_vga_set_decode(void *data, bool state)
> {
> - struct nouveau_drm *drm = pci_get_drvdata(pdev);
> + struct nouveau_drm *drm = (struct nouveau_drm *)data;
> struct nvif_object *device = &drm->client.device.object;
>
> if (drm->client.device.info.family == NV_DEVICE_INFO_V0_CURIE &&
> @@ -103,7 +103,7 @@ nouveau_vga_init(struct nouveau_drm *drm)
> return;
> pdev = to_pci_dev(dev->dev);
>
> - vga_client_register(pdev, nouveau_vga_set_decode);
> + vga_client_register(pdev, nouveau_vga_set_decode, drm);
>
> /* don't register Thunderbolt eGPU with vga_switcheroo */
> if (pci_is_thunderbolt_attached(pdev))
> diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
> index 9523240110a6..cf8a6bd00c77 100644
> --- a/drivers/gpu/drm/radeon/radeon_device.c
> +++ b/drivers/gpu/drm/radeon/radeon_device.c
> @@ -1076,10 +1076,9 @@ void radeon_combios_fini(struct radeon_device *rdev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int radeon_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int radeon_vga_set_decode(void *data, bool state)
> {
> - struct drm_device *dev = pci_get_drvdata(pdev);
> - struct radeon_device *rdev = dev->dev_private;
> + struct radeon_device *rdev = (struct radeon_device *)data;
> radeon_vga_set_state(rdev, state);
> if (state)
> return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM |
> @@ -1431,7 +1430,7 @@ int radeon_device_init(struct radeon_device *rdev,
> /* if we have > 1 VGA cards, then disable the radeon VGA resources */
> /* this will fail for cards that aren't VGA class devices, just
> * ignore it */
> - vga_client_register(rdev->pdev, radeon_vga_set_decode);
> + vga_client_register(rdev->pdev, radeon_vga_set_decode, rdev);
>
> if (rdev->flags & RADEON_IS_PX)
> runtime = true;
> diff --git a/drivers/pci/vgaarb.c b/drivers/pci/vgaarb.c
> index 3de05aee7859..3e58b2c05c85 100644
> --- a/drivers/pci/vgaarb.c
> +++ b/drivers/pci/vgaarb.c
> @@ -51,7 +51,8 @@ struct vga_device {
> unsigned int mem_norm_cnt; /* normal MEM count */
> bool bridge_has_one_vga;
> bool is_firmware_default; /* device selected by firmware */
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode);
> + unsigned int (*set_decode)(void *data, bool decode);
> + void *set_decode_data;
> };
>
> static LIST_HEAD(vga_list);
> @@ -935,6 +936,7 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * vga_client_register - register or unregister a VGA arbitration client
> * @pdev: PCI device of the VGA client
> * @set_decode: VGA decode change callback
> + * @data: private data to pass to callback
> *
> * Clients have two callback mechanisms they can use.
> *
> @@ -956,15 +958,18 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * Returns: 0 on success, -ENODEV on failure
> */
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode))
> + unsigned int (*set_decode)(void *data, bool decode),
> + void *data)
> {
> unsigned long flags;
> struct vga_device *vgadev;
>
> spin_lock_irqsave(&vga_lock, flags);
> vgadev = vgadev_find(pdev);
> - if (vgadev)
> + if (vgadev) {
> vgadev->set_decode = set_decode;
> + vgadev->set_decode_data = data;
> + }
> spin_unlock_irqrestore(&vga_lock, flags);
> if (!vgadev)
> return -ENODEV;
> @@ -1464,7 +1469,7 @@ static void vga_arbiter_notify_clients(void)
> spin_lock_irqsave(&vga_lock, flags);
> list_for_each_entry(vgadev, &vga_list, list) {
> if (vgadev->set_decode) {
> - new_decodes = vgadev->set_decode(vgadev->pdev,
> + new_decodes = vgadev->set_decode(vgadev->set_decode_data,
> new_state);
> vga_update_device_decodes(vgadev, new_decodes);
> }
> diff --git a/drivers/vfio/pci/vfio_pci_core.c b/drivers/vfio/pci/vfio_pci_core.c
> index 6757054e9d87..b04ce3ded08c 100644
> --- a/drivers/vfio/pci/vfio_pci_core.c
> +++ b/drivers/vfio/pci/vfio_pci_core.c
> @@ -162,9 +162,10 @@ static inline void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
> * has no way to get to it and routing can be disabled externally at the
> * bridge.
> */
> -static unsigned int vfio_pci_set_decode(struct pci_dev *pdev, bool single_vga)
> +static unsigned int vfio_pci_set_decode(void *data, bool single_vga)
> {
> - struct vfio_pci_core_device *vdev = dev_get_drvdata(&pdev->dev);
> + struct vfio_pci_core_device *vdev = data;
> + struct pci_dev *pdev = vdev->pdev;
> struct pci_dev *tmp = NULL;
> unsigned char max_busnr;
> unsigned int decodes;
> @@ -2159,10 +2160,10 @@ static int vfio_pci_vga_init(struct vfio_pci_core_device *vdev)
> if (ret)
> return ret;
>
> - ret = vga_client_register(pdev, vfio_pci_set_decode);
> + ret = vga_client_register(pdev, vfio_pci_set_decode, vdev);
> if (ret)
> return ret;
> - vga_set_legacy_decoding(pdev, vfio_pci_set_decode(pdev, false));
> + vga_set_legacy_decoding(pdev, vfio_pci_set_decode(vdev, false));
> return 0;
> }
>
> diff --git a/include/linux/vgaarb.h b/include/linux/vgaarb.h
> index 97129a1bbb7d..71a364669eaf 100644
> --- a/include/linux/vgaarb.h
> +++ b/include/linux/vgaarb.h
> @@ -33,7 +33,8 @@ struct pci_dev *vga_default_device(void);
> void vga_set_default_device(struct pci_dev *pdev);
> int vga_remove_vgacon(struct pci_dev *pdev);
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state));
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data);
> #else /* CONFIG_VGA_ARB */
> static inline void vga_set_legacy_decoding(struct pci_dev *pdev,
> unsigned int decodes)
> @@ -59,7 +60,8 @@ static inline int vga_remove_vgacon(struct pci_dev *pdev)
> return 0;
> }
> static inline int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state))
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data)
> {
> return 0;
> }
> @@ -97,7 +99,7 @@ static inline int vga_get_uninterruptible(struct pci_dev *pdev,
>
> static inline void vga_client_unregister(struct pci_dev *pdev)
> {
> - vga_client_register(pdev, NULL);
> + vga_client_register(pdev, NULL, NULL);
> }
>
> #endif /* LINUX_VGA_H */
> --
> 2.54.0
>
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-22 7:18 [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2) Dave Airlie
` (2 preceding siblings ...)
2026-09-22 15:05 ` Alex Deucher
@ 2026-09-28 19:33 ` Dave Airlie
2026-09-28 20:00 ` Alex Williamson
2026-09-28 20:14 ` Bjorn Helgaas
5 siblings, 0 replies; 8+ messages in thread
From: Dave Airlie @ 2026-09-28 19:33 UTC (permalink / raw)
To: dri-devel, linux-pci, kvm
Cc: Jason Gunthorpe, Dave Airlie, Alex Williamson, Bjorn Helgaas,
Rodrigo Vivi, Alex Deucher
> This changes the vgaarb client API so that the user can pass a
> private data pointer into the register that will get used in
> the decode callback.
>
> This allows a bunch of pdev conversions in the drivers, and lets
> some future vfio cleanups be nicer.
>
> I'd like to merge this via the drm next tree but also fine with
> it going via pci.
>
> Signed-off-by: Dave Airlie <airlied@redhat.com>
> Cc: Alex Williamson <alex@shazbot.org>
> Cc: Bjorn Helgaas <bhelgaas@google.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: Alex Deucher <alexander.deucher@amd.com>
> ---
> v2: fix loongson (spotted by sashiko)
@Alex Williamson or @Jason Gunthorpe can I get an ack on the vfio
piece, since I think the initial report on this problem came from
Jason.
Dave.
> ---
> drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 +++---
> drivers/gpu/drm/i915/display/intel_vga.c | 7 ++++---
> drivers/gpu/drm/loongson/lsdc_drv.c | 4 ++--
> drivers/gpu/drm/nouveau/nouveau_vga.c | 6 +++---
> drivers/gpu/drm/radeon/radeon_device.c | 7 +++----
> drivers/pci/vgaarb.c | 13 +++++++++----
> drivers/vfio/pci/vfio_pci_core.c | 9 +++++----
> include/linux/vgaarb.h | 8 +++++---
> 8 files changed, 34 insertions(+), 26 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> index 62b5b4a23f17..1344b2b1bd16 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> @@ -1435,10 +1435,10 @@ bool amdgpu_device_should_use_aspm(struct amdgpu_device *adev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int amdgpu_device_vga_set_decode(struct pci_dev *pdev,
> +static unsigned int amdgpu_device_vga_set_decode(void *data,
> bool state)
> {
> - struct amdgpu_device *adev = drm_to_adev(pci_get_drvdata(pdev));
> + struct amdgpu_device *adev = (struct amdgpu_device *)data;
>
> amdgpu_asic_set_vga_state(adev, state);
> if (state)
> @@ -4208,7 +4208,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,
> * ignore it
> */
> if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)
> - vga_client_register(adev->pdev, amdgpu_device_vga_set_decode);
> + vga_client_register(adev->pdev, amdgpu_device_vga_set_decode, adev);
>
> px = amdgpu_device_supports_px(adev);
>
> diff --git a/drivers/gpu/drm/i915/display/intel_vga.c b/drivers/gpu/drm/i915/display/intel_vga.c
> index 4966fd7eea92..0889edb36190 100644
> --- a/drivers/gpu/drm/i915/display/intel_vga.c
> +++ b/drivers/gpu/drm/i915/display/intel_vga.c
> @@ -283,9 +283,10 @@ void intel_vga_disable(struct intel_display *display)
> intel_de_posting_read(display, vga_reg);
> }
>
> -static unsigned int intel_vga_set_decode(struct pci_dev *pdev, bool enable_decode)
> +static unsigned int intel_vga_set_decode(void *data, bool enable_decode)
> {
> - struct intel_display *display = to_intel_display(pdev);
> + struct intel_display *display = (struct intel_display *)data;
> + struct pci_dev *pdev = to_pci_dev(display->drm->dev);
> unsigned int decodes = VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
>
> drm_dbg_kms(display->drm, "%s VGA decode due to VGA arbitration\n",
> @@ -331,7 +332,7 @@ void intel_vga_register(struct intel_display *display)
> * then we do not take part in VGA arbitration and the
> * vga_client_register() fails with -ENODEV.
> */
> - ret = vga_client_register(pdev, intel_vga_set_decode);
> + ret = vga_client_register(pdev, intel_vga_set_decode, display);
> drm_WARN_ON(display->drm, ret && ret != -ENODEV);
> }
>
> diff --git a/drivers/gpu/drm/loongson/lsdc_drv.c b/drivers/gpu/drm/loongson/lsdc_drv.c
> index 3fd828d23271..5a13df31eb90 100644
> --- a/drivers/gpu/drm/loongson/lsdc_drv.c
> +++ b/drivers/gpu/drm/loongson/lsdc_drv.c
> @@ -254,7 +254,7 @@ lsdc_create_device(struct pci_dev *pdev,
>
> /* For multiple GPU driver instance co-exixt in the system */
>
> -static unsigned int lsdc_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int lsdc_vga_set_decode(void *data, bool state)
> {
> return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
> }
> @@ -291,7 +291,7 @@ static int lsdc_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
>
> pci_set_drvdata(pdev, ddev);
>
> - vga_client_register(pdev, lsdc_vga_set_decode);
> + vga_client_register(pdev, lsdc_vga_set_decode, NULL);
>
> drmm_kms_helper_poll_init(ddev);
>
> diff --git a/drivers/gpu/drm/nouveau/nouveau_vga.c b/drivers/gpu/drm/nouveau/nouveau_vga.c
> index 29a801124e56..6662e30466f2 100644
> --- a/drivers/gpu/drm/nouveau/nouveau_vga.c
> +++ b/drivers/gpu/drm/nouveau/nouveau_vga.c
> @@ -9,9 +9,9 @@
> #include "nouveau_vga.h"
>
> static unsigned int
> -nouveau_vga_set_decode(struct pci_dev *pdev, bool state)
> +nouveau_vga_set_decode(void *data, bool state)
> {
> - struct nouveau_drm *drm = pci_get_drvdata(pdev);
> + struct nouveau_drm *drm = (struct nouveau_drm *)data;
> struct nvif_object *device = &drm->client.device.object;
>
> if (drm->client.device.info.family == NV_DEVICE_INFO_V0_CURIE &&
> @@ -103,7 +103,7 @@ nouveau_vga_init(struct nouveau_drm *drm)
> return;
> pdev = to_pci_dev(dev->dev);
>
> - vga_client_register(pdev, nouveau_vga_set_decode);
> + vga_client_register(pdev, nouveau_vga_set_decode, drm);
>
> /* don't register Thunderbolt eGPU with vga_switcheroo */
> if (pci_is_thunderbolt_attached(pdev))
> diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
> index 9523240110a6..cf8a6bd00c77 100644
> --- a/drivers/gpu/drm/radeon/radeon_device.c
> +++ b/drivers/gpu/drm/radeon/radeon_device.c
> @@ -1076,10 +1076,9 @@ void radeon_combios_fini(struct radeon_device *rdev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int radeon_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int radeon_vga_set_decode(void *data, bool state)
> {
> - struct drm_device *dev = pci_get_drvdata(pdev);
> - struct radeon_device *rdev = dev->dev_private;
> + struct radeon_device *rdev = (struct radeon_device *)data;
> radeon_vga_set_state(rdev, state);
> if (state)
> return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM |
> @@ -1431,7 +1430,7 @@ int radeon_device_init(struct radeon_device *rdev,
> /* if we have > 1 VGA cards, then disable the radeon VGA resources */
> /* this will fail for cards that aren't VGA class devices, just
> * ignore it */
> - vga_client_register(rdev->pdev, radeon_vga_set_decode);
> + vga_client_register(rdev->pdev, radeon_vga_set_decode, rdev);
>
> if (rdev->flags & RADEON_IS_PX)
> runtime = true;
> diff --git a/drivers/pci/vgaarb.c b/drivers/pci/vgaarb.c
> index 3de05aee7859..3e58b2c05c85 100644
> --- a/drivers/pci/vgaarb.c
> +++ b/drivers/pci/vgaarb.c
> @@ -51,7 +51,8 @@ struct vga_device {
> unsigned int mem_norm_cnt; /* normal MEM count */
> bool bridge_has_one_vga;
> bool is_firmware_default; /* device selected by firmware */
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode);
> + unsigned int (*set_decode)(void *data, bool decode);
> + void *set_decode_data;
> };
>
> static LIST_HEAD(vga_list);
> @@ -935,6 +936,7 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * vga_client_register - register or unregister a VGA arbitration client
> * @pdev: PCI device of the VGA client
> * @set_decode: VGA decode change callback
> + * @data: private data to pass to callback
> *
> * Clients have two callback mechanisms they can use.
> *
> @@ -956,15 +958,18 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * Returns: 0 on success, -ENODEV on failure
> */
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode))
> + unsigned int (*set_decode)(void *data, bool decode),
> + void *data)
> {
> unsigned long flags;
> struct vga_device *vgadev;
>
> spin_lock_irqsave(&vga_lock, flags);
> vgadev = vgadev_find(pdev);
> - if (vgadev)
> + if (vgadev) {
> vgadev->set_decode = set_decode;
> + vgadev->set_decode_data = data;
> + }
> spin_unlock_irqrestore(&vga_lock, flags);
> if (!vgadev)
> return -ENODEV;
> @@ -1464,7 +1469,7 @@ static void vga_arbiter_notify_clients(void)
> spin_lock_irqsave(&vga_lock, flags);
> list_for_each_entry(vgadev, &vga_list, list) {
> if (vgadev->set_decode) {
> - new_decodes = vgadev->set_decode(vgadev->pdev,
> + new_decodes = vgadev->set_decode(vgadev->set_decode_data,
> new_state);
> vga_update_device_decodes(vgadev, new_decodes);
> }
> diff --git a/drivers/vfio/pci/vfio_pci_core.c b/drivers/vfio/pci/vfio_pci_core.c
> index 6757054e9d87..b04ce3ded08c 100644
> --- a/drivers/vfio/pci/vfio_pci_core.c
> +++ b/drivers/vfio/pci/vfio_pci_core.c
> @@ -162,9 +162,10 @@ static inline void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
> * has no way to get to it and routing can be disabled externally at the
> * bridge.
> */
> -static unsigned int vfio_pci_set_decode(struct pci_dev *pdev, bool single_vga)
> +static unsigned int vfio_pci_set_decode(void *data, bool single_vga)
> {
> - struct vfio_pci_core_device *vdev = dev_get_drvdata(&pdev->dev);
> + struct vfio_pci_core_device *vdev = data;
> + struct pci_dev *pdev = vdev->pdev;
> struct pci_dev *tmp = NULL;
> unsigned char max_busnr;
> unsigned int decodes;
> @@ -2159,10 +2160,10 @@ static int vfio_pci_vga_init(struct vfio_pci_core_device *vdev)
> if (ret)
> return ret;
>
> - ret = vga_client_register(pdev, vfio_pci_set_decode);
> + ret = vga_client_register(pdev, vfio_pci_set_decode, vdev);
> if (ret)
> return ret;
> - vga_set_legacy_decoding(pdev, vfio_pci_set_decode(pdev, false));
> + vga_set_legacy_decoding(pdev, vfio_pci_set_decode(vdev, false));
> return 0;
> }
>
> diff --git a/include/linux/vgaarb.h b/include/linux/vgaarb.h
> index 97129a1bbb7d..71a364669eaf 100644
> --- a/include/linux/vgaarb.h
> +++ b/include/linux/vgaarb.h
> @@ -33,7 +33,8 @@ struct pci_dev *vga_default_device(void);
> void vga_set_default_device(struct pci_dev *pdev);
> int vga_remove_vgacon(struct pci_dev *pdev);
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state));
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data);
> #else /* CONFIG_VGA_ARB */
> static inline void vga_set_legacy_decoding(struct pci_dev *pdev,
> unsigned int decodes)
> @@ -59,7 +60,8 @@ static inline int vga_remove_vgacon(struct pci_dev *pdev)
> return 0;
> }
> static inline int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state))
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data)
> {
> return 0;
> }
> @@ -97,7 +99,7 @@ static inline int vga_get_uninterruptible(struct pci_dev *pdev,
>
> static inline void vga_client_unregister(struct pci_dev *pdev)
> {
> - vga_client_register(pdev, NULL);
> + vga_client_register(pdev, NULL, NULL);
> }
>
> #endif /* LINUX_VGA_H */
> --
> 2.54.0
>
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-22 7:18 [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2) Dave Airlie
` (3 preceding siblings ...)
2026-09-28 19:33 ` Dave Airlie
@ 2026-09-28 20:00 ` Alex Williamson
2026-10-01 1:08 ` David Airlie
2026-09-28 20:14 ` Bjorn Helgaas
5 siblings, 1 reply; 8+ messages in thread
From: Alex Williamson @ 2026-09-28 20:00 UTC (permalink / raw)
To: Dave Airlie
Cc: dri-devel, linux-pci, kvm, Jason Gunthorpe, Dave Airlie,
Bjorn Helgaas, Rodrigo Vivi, Alex Deucher, alex,
Simon Song (SW-GPU)
On Tue, 22 Sep 2026 17:18:07 +1000
Dave Airlie <airlied@gmail.com> wrote:
> From: Dave Airlie <airlied@redhat.com>
>
> This changes the vgaarb client API so that the user can pass a
> private data pointer into the register that will get used in
> the decode callback.
>
> This allows a bunch of pdev conversions in the drivers, and lets
> some future vfio cleanups be nicer.
>
> I'd like to merge this via the drm next tree but also fine with
> it going via pci.
>
> Signed-off-by: Dave Airlie <airlied@redhat.com>
> Cc: Alex Williamson <alex@shazbot.org>
> Cc: Bjorn Helgaas <bhelgaas@google.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: Alex Deucher <alexander.deucher@amd.com>
> ---
> v2: fix loongson (spotted by sashiko)
> ---
> drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 +++---
> drivers/gpu/drm/i915/display/intel_vga.c | 7 ++++---
> drivers/gpu/drm/loongson/lsdc_drv.c | 4 ++--
> drivers/gpu/drm/nouveau/nouveau_vga.c | 6 +++---
> drivers/gpu/drm/radeon/radeon_device.c | 7 +++----
> drivers/pci/vgaarb.c | 13 +++++++++----
> drivers/vfio/pci/vfio_pci_core.c | 9 +++++----
> include/linux/vgaarb.h | 8 +++++---
> 8 files changed, 34 insertions(+), 26 deletions(-)
Acked-by: Alex Williamson <alex@shazbot.org>
Preemptively, could this get merged via a topic branch that we could
share in case further drvdata cleanup arrives in vfio-pci this cycle?
I'm imagining this might also be a good time to push vgaarb
registration out of vfio-pci-core as well. Thanks,
Alex
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> index 62b5b4a23f17..1344b2b1bd16 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> @@ -1435,10 +1435,10 @@ bool amdgpu_device_should_use_aspm(struct amdgpu_device *adev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int amdgpu_device_vga_set_decode(struct pci_dev *pdev,
> +static unsigned int amdgpu_device_vga_set_decode(void *data,
> bool state)
> {
> - struct amdgpu_device *adev = drm_to_adev(pci_get_drvdata(pdev));
> + struct amdgpu_device *adev = (struct amdgpu_device *)data;
>
> amdgpu_asic_set_vga_state(adev, state);
> if (state)
> @@ -4208,7 +4208,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,
> * ignore it
> */
> if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)
> - vga_client_register(adev->pdev, amdgpu_device_vga_set_decode);
> + vga_client_register(adev->pdev, amdgpu_device_vga_set_decode, adev);
>
> px = amdgpu_device_supports_px(adev);
>
> diff --git a/drivers/gpu/drm/i915/display/intel_vga.c b/drivers/gpu/drm/i915/display/intel_vga.c
> index 4966fd7eea92..0889edb36190 100644
> --- a/drivers/gpu/drm/i915/display/intel_vga.c
> +++ b/drivers/gpu/drm/i915/display/intel_vga.c
> @@ -283,9 +283,10 @@ void intel_vga_disable(struct intel_display *display)
> intel_de_posting_read(display, vga_reg);
> }
>
> -static unsigned int intel_vga_set_decode(struct pci_dev *pdev, bool enable_decode)
> +static unsigned int intel_vga_set_decode(void *data, bool enable_decode)
> {
> - struct intel_display *display = to_intel_display(pdev);
> + struct intel_display *display = (struct intel_display *)data;
> + struct pci_dev *pdev = to_pci_dev(display->drm->dev);
> unsigned int decodes = VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
>
> drm_dbg_kms(display->drm, "%s VGA decode due to VGA arbitration\n",
> @@ -331,7 +332,7 @@ void intel_vga_register(struct intel_display *display)
> * then we do not take part in VGA arbitration and the
> * vga_client_register() fails with -ENODEV.
> */
> - ret = vga_client_register(pdev, intel_vga_set_decode);
> + ret = vga_client_register(pdev, intel_vga_set_decode, display);
> drm_WARN_ON(display->drm, ret && ret != -ENODEV);
> }
>
> diff --git a/drivers/gpu/drm/loongson/lsdc_drv.c b/drivers/gpu/drm/loongson/lsdc_drv.c
> index 3fd828d23271..5a13df31eb90 100644
> --- a/drivers/gpu/drm/loongson/lsdc_drv.c
> +++ b/drivers/gpu/drm/loongson/lsdc_drv.c
> @@ -254,7 +254,7 @@ lsdc_create_device(struct pci_dev *pdev,
>
> /* For multiple GPU driver instance co-exixt in the system */
>
> -static unsigned int lsdc_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int lsdc_vga_set_decode(void *data, bool state)
> {
> return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
> }
> @@ -291,7 +291,7 @@ static int lsdc_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
>
> pci_set_drvdata(pdev, ddev);
>
> - vga_client_register(pdev, lsdc_vga_set_decode);
> + vga_client_register(pdev, lsdc_vga_set_decode, NULL);
>
> drmm_kms_helper_poll_init(ddev);
>
> diff --git a/drivers/gpu/drm/nouveau/nouveau_vga.c b/drivers/gpu/drm/nouveau/nouveau_vga.c
> index 29a801124e56..6662e30466f2 100644
> --- a/drivers/gpu/drm/nouveau/nouveau_vga.c
> +++ b/drivers/gpu/drm/nouveau/nouveau_vga.c
> @@ -9,9 +9,9 @@
> #include "nouveau_vga.h"
>
> static unsigned int
> -nouveau_vga_set_decode(struct pci_dev *pdev, bool state)
> +nouveau_vga_set_decode(void *data, bool state)
> {
> - struct nouveau_drm *drm = pci_get_drvdata(pdev);
> + struct nouveau_drm *drm = (struct nouveau_drm *)data;
> struct nvif_object *device = &drm->client.device.object;
>
> if (drm->client.device.info.family == NV_DEVICE_INFO_V0_CURIE &&
> @@ -103,7 +103,7 @@ nouveau_vga_init(struct nouveau_drm *drm)
> return;
> pdev = to_pci_dev(dev->dev);
>
> - vga_client_register(pdev, nouveau_vga_set_decode);
> + vga_client_register(pdev, nouveau_vga_set_decode, drm);
>
> /* don't register Thunderbolt eGPU with vga_switcheroo */
> if (pci_is_thunderbolt_attached(pdev))
> diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
> index 9523240110a6..cf8a6bd00c77 100644
> --- a/drivers/gpu/drm/radeon/radeon_device.c
> +++ b/drivers/gpu/drm/radeon/radeon_device.c
> @@ -1076,10 +1076,9 @@ void radeon_combios_fini(struct radeon_device *rdev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int radeon_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int radeon_vga_set_decode(void *data, bool state)
> {
> - struct drm_device *dev = pci_get_drvdata(pdev);
> - struct radeon_device *rdev = dev->dev_private;
> + struct radeon_device *rdev = (struct radeon_device *)data;
> radeon_vga_set_state(rdev, state);
> if (state)
> return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM |
> @@ -1431,7 +1430,7 @@ int radeon_device_init(struct radeon_device *rdev,
> /* if we have > 1 VGA cards, then disable the radeon VGA resources */
> /* this will fail for cards that aren't VGA class devices, just
> * ignore it */
> - vga_client_register(rdev->pdev, radeon_vga_set_decode);
> + vga_client_register(rdev->pdev, radeon_vga_set_decode, rdev);
>
> if (rdev->flags & RADEON_IS_PX)
> runtime = true;
> diff --git a/drivers/pci/vgaarb.c b/drivers/pci/vgaarb.c
> index 3de05aee7859..3e58b2c05c85 100644
> --- a/drivers/pci/vgaarb.c
> +++ b/drivers/pci/vgaarb.c
> @@ -51,7 +51,8 @@ struct vga_device {
> unsigned int mem_norm_cnt; /* normal MEM count */
> bool bridge_has_one_vga;
> bool is_firmware_default; /* device selected by firmware */
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode);
> + unsigned int (*set_decode)(void *data, bool decode);
> + void *set_decode_data;
> };
>
> static LIST_HEAD(vga_list);
> @@ -935,6 +936,7 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * vga_client_register - register or unregister a VGA arbitration client
> * @pdev: PCI device of the VGA client
> * @set_decode: VGA decode change callback
> + * @data: private data to pass to callback
> *
> * Clients have two callback mechanisms they can use.
> *
> @@ -956,15 +958,18 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * Returns: 0 on success, -ENODEV on failure
> */
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode))
> + unsigned int (*set_decode)(void *data, bool decode),
> + void *data)
> {
> unsigned long flags;
> struct vga_device *vgadev;
>
> spin_lock_irqsave(&vga_lock, flags);
> vgadev = vgadev_find(pdev);
> - if (vgadev)
> + if (vgadev) {
> vgadev->set_decode = set_decode;
> + vgadev->set_decode_data = data;
> + }
> spin_unlock_irqrestore(&vga_lock, flags);
> if (!vgadev)
> return -ENODEV;
> @@ -1464,7 +1469,7 @@ static void vga_arbiter_notify_clients(void)
> spin_lock_irqsave(&vga_lock, flags);
> list_for_each_entry(vgadev, &vga_list, list) {
> if (vgadev->set_decode) {
> - new_decodes = vgadev->set_decode(vgadev->pdev,
> + new_decodes = vgadev->set_decode(vgadev->set_decode_data,
> new_state);
> vga_update_device_decodes(vgadev, new_decodes);
> }
> diff --git a/drivers/vfio/pci/vfio_pci_core.c b/drivers/vfio/pci/vfio_pci_core.c
> index 6757054e9d87..b04ce3ded08c 100644
> --- a/drivers/vfio/pci/vfio_pci_core.c
> +++ b/drivers/vfio/pci/vfio_pci_core.c
> @@ -162,9 +162,10 @@ static inline void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
> * has no way to get to it and routing can be disabled externally at the
> * bridge.
> */
> -static unsigned int vfio_pci_set_decode(struct pci_dev *pdev, bool single_vga)
> +static unsigned int vfio_pci_set_decode(void *data, bool single_vga)
> {
> - struct vfio_pci_core_device *vdev = dev_get_drvdata(&pdev->dev);
> + struct vfio_pci_core_device *vdev = data;
> + struct pci_dev *pdev = vdev->pdev;
> struct pci_dev *tmp = NULL;
> unsigned char max_busnr;
> unsigned int decodes;
> @@ -2159,10 +2160,10 @@ static int vfio_pci_vga_init(struct vfio_pci_core_device *vdev)
> if (ret)
> return ret;
>
> - ret = vga_client_register(pdev, vfio_pci_set_decode);
> + ret = vga_client_register(pdev, vfio_pci_set_decode, vdev);
> if (ret)
> return ret;
> - vga_set_legacy_decoding(pdev, vfio_pci_set_decode(pdev, false));
> + vga_set_legacy_decoding(pdev, vfio_pci_set_decode(vdev, false));
> return 0;
> }
>
> diff --git a/include/linux/vgaarb.h b/include/linux/vgaarb.h
> index 97129a1bbb7d..71a364669eaf 100644
> --- a/include/linux/vgaarb.h
> +++ b/include/linux/vgaarb.h
> @@ -33,7 +33,8 @@ struct pci_dev *vga_default_device(void);
> void vga_set_default_device(struct pci_dev *pdev);
> int vga_remove_vgacon(struct pci_dev *pdev);
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state));
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data);
> #else /* CONFIG_VGA_ARB */
> static inline void vga_set_legacy_decoding(struct pci_dev *pdev,
> unsigned int decodes)
> @@ -59,7 +60,8 @@ static inline int vga_remove_vgacon(struct pci_dev *pdev)
> return 0;
> }
> static inline int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state))
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data)
> {
> return 0;
> }
> @@ -97,7 +99,7 @@ static inline int vga_get_uninterruptible(struct pci_dev *pdev,
>
> static inline void vga_client_unregister(struct pci_dev *pdev)
> {
> - vga_client_register(pdev, NULL);
> + vga_client_register(pdev, NULL, NULL);
> }
>
> #endif /* LINUX_VGA_H */
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-28 20:00 ` Alex Williamson
@ 2026-10-01 1:08 ` David Airlie
0 siblings, 0 replies; 8+ messages in thread
From: David Airlie @ 2026-10-01 1:08 UTC (permalink / raw)
To: Alex Williamson
Cc: Dave Airlie, dri-devel, linux-pci, kvm, Jason Gunthorpe,
Bjorn Helgaas, Rodrigo Vivi, Alex Deucher, Simon Song (SW-GPU)
On Tue, Sep 29, 2026 at 6:06 AM Alex Williamson <alex@shazbot.org> wrote:
>
> On Tue, 22 Sep 2026 17:18:07 +1000
> Dave Airlie <airlied@gmail.com> wrote:
>
> > From: Dave Airlie <airlied@redhat.com>
> >
> > This changes the vgaarb client API so that the user can pass a
> > private data pointer into the register that will get used in
> > the decode callback.
> >
> > This allows a bunch of pdev conversions in the drivers, and lets
> > some future vfio cleanups be nicer.
> >
> > I'd like to merge this via the drm next tree but also fine with
> > it going via pci.
> >
> > Signed-off-by: Dave Airlie <airlied@redhat.com>
> > Cc: Alex Williamson <alex@shazbot.org>
> > Cc: Bjorn Helgaas <bhelgaas@google.com>
> > Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> > Cc: Alex Deucher <alexander.deucher@amd.com>
> > ---
> > v2: fix loongson (spotted by sashiko)
> > ---
> > drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 +++---
> > drivers/gpu/drm/i915/display/intel_vga.c | 7 ++++---
> > drivers/gpu/drm/loongson/lsdc_drv.c | 4 ++--
> > drivers/gpu/drm/nouveau/nouveau_vga.c | 6 +++---
> > drivers/gpu/drm/radeon/radeon_device.c | 7 +++----
> > drivers/pci/vgaarb.c | 13 +++++++++----
> > drivers/vfio/pci/vfio_pci_core.c | 9 +++++----
> > include/linux/vgaarb.h | 8 +++++---
> > 8 files changed, 34 insertions(+), 26 deletions(-)
>
>
> Acked-by: Alex Williamson <alex@shazbot.org>
>
> Preemptively, could this get merged via a topic branch that we could
> share in case further drvdata cleanup arrives in vfio-pci this cycle?
>
> I'm imagining this might also be a good time to push vgaarb
> registration out of vfio-pci-core as well. Thanks,
>
Thanks Alex and Bjorn,
Okay I've cleaned up the last few bits from Bjorn, added lines and
created a drm topic branch
https://gitlab.freedesktop.org/drm/kernel topic/pci-vgaarb-rework
I'll send a PR merge this into drm-next and you can work off it as
well if you need to.
Dave.
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2)
2026-09-22 7:18 [PATCH] pci/vgaarb: pass a data pointer to be used in the decode callback (v2) Dave Airlie
` (4 preceding siblings ...)
2026-09-28 20:00 ` Alex Williamson
@ 2026-09-28 20:14 ` Bjorn Helgaas
5 siblings, 0 replies; 8+ messages in thread
From: Bjorn Helgaas @ 2026-09-28 20:14 UTC (permalink / raw)
To: Dave Airlie
Cc: dri-devel, linux-pci, kvm, Jason Gunthorpe, Dave Airlie,
Alex Williamson, Bjorn Helgaas, Rodrigo Vivi, Alex Deucher
On Tue, Sep 22, 2026 at 05:18:07PM +1000, Dave Airlie wrote:
> From: Dave Airlie <airlied@redhat.com>
>
> This changes the vgaarb client API so that the user can pass a
> private data pointer into the register that will get used in
> the decode callback.
>
> This allows a bunch of pdev conversions in the drivers, and lets
> some future vfio cleanups be nicer.
>
> I'd like to merge this via the drm next tree but also fine with
> it going via pci.
>
> Signed-off-by: Dave Airlie <airlied@redhat.com>
> Cc: Alex Williamson <alex@shazbot.org>
> Cc: Bjorn Helgaas <bhelgaas@google.com>
> Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
> Cc: Alex Deucher <alexander.deucher@amd.com>
The only diff between v1
(https://lore.kernel.org/all/20260922064111.2468741-1-airlied@gmail.com)
and this is the trivial Loongson change.
It looks like the new kernel-doc warning is still there:
https://lore.kernel.org/all/202609241015.1yXHBzfy-lkp@intel.com/
And it would still be nice to update the subject line as I mentioned:
https://lore.kernel.org/all/20260924191253.GA1994586@bhelgaas
I'm still fine with it being merged via drm.
Acked-by: Bjorn Helgaas <bhelgaas@google.com>
> ---
> v2: fix loongson (spotted by sashiko)
> ---
> drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 6 +++---
> drivers/gpu/drm/i915/display/intel_vga.c | 7 ++++---
> drivers/gpu/drm/loongson/lsdc_drv.c | 4 ++--
> drivers/gpu/drm/nouveau/nouveau_vga.c | 6 +++---
> drivers/gpu/drm/radeon/radeon_device.c | 7 +++----
> drivers/pci/vgaarb.c | 13 +++++++++----
> drivers/vfio/pci/vfio_pci_core.c | 9 +++++----
> include/linux/vgaarb.h | 8 +++++---
> 8 files changed, 34 insertions(+), 26 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> index 62b5b4a23f17..1344b2b1bd16 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
> @@ -1435,10 +1435,10 @@ bool amdgpu_device_should_use_aspm(struct amdgpu_device *adev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int amdgpu_device_vga_set_decode(struct pci_dev *pdev,
> +static unsigned int amdgpu_device_vga_set_decode(void *data,
> bool state)
> {
> - struct amdgpu_device *adev = drm_to_adev(pci_get_drvdata(pdev));
> + struct amdgpu_device *adev = (struct amdgpu_device *)data;
>
> amdgpu_asic_set_vga_state(adev, state);
> if (state)
> @@ -4208,7 +4208,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,
> * ignore it
> */
> if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)
> - vga_client_register(adev->pdev, amdgpu_device_vga_set_decode);
> + vga_client_register(adev->pdev, amdgpu_device_vga_set_decode, adev);
>
> px = amdgpu_device_supports_px(adev);
>
> diff --git a/drivers/gpu/drm/i915/display/intel_vga.c b/drivers/gpu/drm/i915/display/intel_vga.c
> index 4966fd7eea92..0889edb36190 100644
> --- a/drivers/gpu/drm/i915/display/intel_vga.c
> +++ b/drivers/gpu/drm/i915/display/intel_vga.c
> @@ -283,9 +283,10 @@ void intel_vga_disable(struct intel_display *display)
> intel_de_posting_read(display, vga_reg);
> }
>
> -static unsigned int intel_vga_set_decode(struct pci_dev *pdev, bool enable_decode)
> +static unsigned int intel_vga_set_decode(void *data, bool enable_decode)
> {
> - struct intel_display *display = to_intel_display(pdev);
> + struct intel_display *display = (struct intel_display *)data;
> + struct pci_dev *pdev = to_pci_dev(display->drm->dev);
> unsigned int decodes = VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
>
> drm_dbg_kms(display->drm, "%s VGA decode due to VGA arbitration\n",
> @@ -331,7 +332,7 @@ void intel_vga_register(struct intel_display *display)
> * then we do not take part in VGA arbitration and the
> * vga_client_register() fails with -ENODEV.
> */
> - ret = vga_client_register(pdev, intel_vga_set_decode);
> + ret = vga_client_register(pdev, intel_vga_set_decode, display);
> drm_WARN_ON(display->drm, ret && ret != -ENODEV);
> }
>
> diff --git a/drivers/gpu/drm/loongson/lsdc_drv.c b/drivers/gpu/drm/loongson/lsdc_drv.c
> index 3fd828d23271..5a13df31eb90 100644
> --- a/drivers/gpu/drm/loongson/lsdc_drv.c
> +++ b/drivers/gpu/drm/loongson/lsdc_drv.c
> @@ -254,7 +254,7 @@ lsdc_create_device(struct pci_dev *pdev,
>
> /* For multiple GPU driver instance co-exixt in the system */
>
> -static unsigned int lsdc_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int lsdc_vga_set_decode(void *data, bool state)
> {
> return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM;
> }
> @@ -291,7 +291,7 @@ static int lsdc_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
>
> pci_set_drvdata(pdev, ddev);
>
> - vga_client_register(pdev, lsdc_vga_set_decode);
> + vga_client_register(pdev, lsdc_vga_set_decode, NULL);
>
> drmm_kms_helper_poll_init(ddev);
>
> diff --git a/drivers/gpu/drm/nouveau/nouveau_vga.c b/drivers/gpu/drm/nouveau/nouveau_vga.c
> index 29a801124e56..6662e30466f2 100644
> --- a/drivers/gpu/drm/nouveau/nouveau_vga.c
> +++ b/drivers/gpu/drm/nouveau/nouveau_vga.c
> @@ -9,9 +9,9 @@
> #include "nouveau_vga.h"
>
> static unsigned int
> -nouveau_vga_set_decode(struct pci_dev *pdev, bool state)
> +nouveau_vga_set_decode(void *data, bool state)
> {
> - struct nouveau_drm *drm = pci_get_drvdata(pdev);
> + struct nouveau_drm *drm = (struct nouveau_drm *)data;
> struct nvif_object *device = &drm->client.device.object;
>
> if (drm->client.device.info.family == NV_DEVICE_INFO_V0_CURIE &&
> @@ -103,7 +103,7 @@ nouveau_vga_init(struct nouveau_drm *drm)
> return;
> pdev = to_pci_dev(dev->dev);
>
> - vga_client_register(pdev, nouveau_vga_set_decode);
> + vga_client_register(pdev, nouveau_vga_set_decode, drm);
>
> /* don't register Thunderbolt eGPU with vga_switcheroo */
> if (pci_is_thunderbolt_attached(pdev))
> diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
> index 9523240110a6..cf8a6bd00c77 100644
> --- a/drivers/gpu/drm/radeon/radeon_device.c
> +++ b/drivers/gpu/drm/radeon/radeon_device.c
> @@ -1076,10 +1076,9 @@ void radeon_combios_fini(struct radeon_device *rdev)
> * Enable/disable vga decode (all asics).
> * Returns VGA resource flags.
> */
> -static unsigned int radeon_vga_set_decode(struct pci_dev *pdev, bool state)
> +static unsigned int radeon_vga_set_decode(void *data, bool state)
> {
> - struct drm_device *dev = pci_get_drvdata(pdev);
> - struct radeon_device *rdev = dev->dev_private;
> + struct radeon_device *rdev = (struct radeon_device *)data;
> radeon_vga_set_state(rdev, state);
> if (state)
> return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM |
> @@ -1431,7 +1430,7 @@ int radeon_device_init(struct radeon_device *rdev,
> /* if we have > 1 VGA cards, then disable the radeon VGA resources */
> /* this will fail for cards that aren't VGA class devices, just
> * ignore it */
> - vga_client_register(rdev->pdev, radeon_vga_set_decode);
> + vga_client_register(rdev->pdev, radeon_vga_set_decode, rdev);
>
> if (rdev->flags & RADEON_IS_PX)
> runtime = true;
> diff --git a/drivers/pci/vgaarb.c b/drivers/pci/vgaarb.c
> index 3de05aee7859..3e58b2c05c85 100644
> --- a/drivers/pci/vgaarb.c
> +++ b/drivers/pci/vgaarb.c
> @@ -51,7 +51,8 @@ struct vga_device {
> unsigned int mem_norm_cnt; /* normal MEM count */
> bool bridge_has_one_vga;
> bool is_firmware_default; /* device selected by firmware */
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode);
> + unsigned int (*set_decode)(void *data, bool decode);
> + void *set_decode_data;
> };
>
> static LIST_HEAD(vga_list);
> @@ -935,6 +936,7 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * vga_client_register - register or unregister a VGA arbitration client
> * @pdev: PCI device of the VGA client
> * @set_decode: VGA decode change callback
> + * @data: private data to pass to callback
> *
> * Clients have two callback mechanisms they can use.
> *
> @@ -956,15 +958,18 @@ EXPORT_SYMBOL(vga_set_legacy_decoding);
> * Returns: 0 on success, -ENODEV on failure
> */
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool decode))
> + unsigned int (*set_decode)(void *data, bool decode),
> + void *data)
> {
> unsigned long flags;
> struct vga_device *vgadev;
>
> spin_lock_irqsave(&vga_lock, flags);
> vgadev = vgadev_find(pdev);
> - if (vgadev)
> + if (vgadev) {
> vgadev->set_decode = set_decode;
> + vgadev->set_decode_data = data;
> + }
> spin_unlock_irqrestore(&vga_lock, flags);
> if (!vgadev)
> return -ENODEV;
> @@ -1464,7 +1469,7 @@ static void vga_arbiter_notify_clients(void)
> spin_lock_irqsave(&vga_lock, flags);
> list_for_each_entry(vgadev, &vga_list, list) {
> if (vgadev->set_decode) {
> - new_decodes = vgadev->set_decode(vgadev->pdev,
> + new_decodes = vgadev->set_decode(vgadev->set_decode_data,
> new_state);
> vga_update_device_decodes(vgadev, new_decodes);
> }
> diff --git a/drivers/vfio/pci/vfio_pci_core.c b/drivers/vfio/pci/vfio_pci_core.c
> index 6757054e9d87..b04ce3ded08c 100644
> --- a/drivers/vfio/pci/vfio_pci_core.c
> +++ b/drivers/vfio/pci/vfio_pci_core.c
> @@ -162,9 +162,10 @@ static inline void vfio_pci_core_debugfs_init(struct vfio_pci_core_device *vdev)
> * has no way to get to it and routing can be disabled externally at the
> * bridge.
> */
> -static unsigned int vfio_pci_set_decode(struct pci_dev *pdev, bool single_vga)
> +static unsigned int vfio_pci_set_decode(void *data, bool single_vga)
> {
> - struct vfio_pci_core_device *vdev = dev_get_drvdata(&pdev->dev);
> + struct vfio_pci_core_device *vdev = data;
> + struct pci_dev *pdev = vdev->pdev;
> struct pci_dev *tmp = NULL;
> unsigned char max_busnr;
> unsigned int decodes;
> @@ -2159,10 +2160,10 @@ static int vfio_pci_vga_init(struct vfio_pci_core_device *vdev)
> if (ret)
> return ret;
>
> - ret = vga_client_register(pdev, vfio_pci_set_decode);
> + ret = vga_client_register(pdev, vfio_pci_set_decode, vdev);
> if (ret)
> return ret;
> - vga_set_legacy_decoding(pdev, vfio_pci_set_decode(pdev, false));
> + vga_set_legacy_decoding(pdev, vfio_pci_set_decode(vdev, false));
> return 0;
> }
>
> diff --git a/include/linux/vgaarb.h b/include/linux/vgaarb.h
> index 97129a1bbb7d..71a364669eaf 100644
> --- a/include/linux/vgaarb.h
> +++ b/include/linux/vgaarb.h
> @@ -33,7 +33,8 @@ struct pci_dev *vga_default_device(void);
> void vga_set_default_device(struct pci_dev *pdev);
> int vga_remove_vgacon(struct pci_dev *pdev);
> int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state));
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data);
> #else /* CONFIG_VGA_ARB */
> static inline void vga_set_legacy_decoding(struct pci_dev *pdev,
> unsigned int decodes)
> @@ -59,7 +60,8 @@ static inline int vga_remove_vgacon(struct pci_dev *pdev)
> return 0;
> }
> static inline int vga_client_register(struct pci_dev *pdev,
> - unsigned int (*set_decode)(struct pci_dev *pdev, bool state))
> + unsigned int (*set_decode)(void *data, bool state),
> + void *data)
> {
> return 0;
> }
> @@ -97,7 +99,7 @@ static inline int vga_get_uninterruptible(struct pci_dev *pdev,
>
> static inline void vga_client_unregister(struct pci_dev *pdev)
> {
> - vga_client_register(pdev, NULL);
> + vga_client_register(pdev, NULL, NULL);
> }
>
> #endif /* LINUX_VGA_H */
> --
> 2.54.0
>
^ permalink raw reply [flat|nested] 8+ messages in thread