Linux s390 Architecture development
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Steffen Eiden" <seiden@linux.ibm.com>
Cc: kvmarm@lists.linux.dev, linux-s390@vger.kernel.org,
	"Marc Zyngier" <maz@kernel.org>,
	"Christian Borntraeger" <borntraeger@linux.ibm.vom>,
	kvm@vger.kernel.org, "Heiko Carstens" <hca@linux.ibm.com>,
	"Alexander Gordeev" <agordeev@linux.ibm.com>,
	"Oliver Upton" <oupton@kernel.org>,
	"Vasily Gorbik" <gor@linux.ibm.com>
Subject: Re: [PATCH v6 01/33] vfio: Use file-based reference counting for KVM
Date: Wed, 12 Aug 2026 16:00:48 +0000	[thread overview]
Message-ID: <20260812160049.4D4321F000E9@smtp.kernel.org> (raw)
In-Reply-To: <20260812153631.3376090-2-seiden@linux.ibm.com>

Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
- [Critical] VFIO retains a dangling weak pointer to the KVM VM `struct file` when the VM fd is closed, leading to use-after-free and type confusion if the file memory is reallocated.
- [Medium] Direct, unsafe access to the RCU-protected pointer `kvm->file` without using RCU primitives.
--

--- Patch [1]: [PATCH v6 01/33] vfio: Use file-based reference counting for KVM ---
commit fbb73952530ea819e76b37873395b8b6ce2e0444
Author: Steffen Eiden <seiden@linux.ibm.com>

vfio: Use file-based reference counting for KVM

This commit replaces manual module reference counting with file-based
reference counting for KVM integration. It updates the VFIO-KVM interface
to pass struct file pointers instead of struct kvm pointers, relying on
get_file_active() and fput() for reference management.

> diff --git a/drivers/s390/crypto/vfio_ap_ops.c b/drivers/s390/crypto/vfio_ap_ops.c
> index 99a0efd999ef9..875e67063d8e5 100644
> --- a/drivers/s390/crypto/vfio_ap_ops.c
> +++ b/drivers/s390/crypto/vfio_ap_ops.c
[ ... ]
> @@ -1822,12 +1823,25 @@ static const struct attribute_group *vfio_ap_mdev_attr_groups[] = {
>   * @matrix_mdev: a mediated matrix device
>   * @kvm: reference to KVM instance
>   *
> - * Return: 0 if no other mediated matrix device has a reference to @kvm;
> - * otherwise, returns an -EPERM.
> + * Returns: 0 if the reference to kvm is successfully retrieved from @kvm_file
> + * and set into @matrix_mdev; otherwise, returns:
> + *	-ENOENT if a reference to kvm could not be retrieved from @kvm_file
> + *	-EPERM if another mediated matrix device already has a reference to the same kvm instance
>   */
>  static int vfio_ap_mdev_set_kvm(struct ap_matrix_mdev *matrix_mdev,
> -				struct kvm *kvm)
> +				struct file **kvm_file)
>  {
> +	struct file *kvm_file_ref __free(fput) = NULL;
> +	struct kvm *kvm;
> +
> +	kvm_file_ref = get_file_active(kvm_file);
> +	if (!kvm_file_ref)
> +		return -ENOENT;
> +
> +	kvm = kvm_file_ref->private_data;
> +	if (!kvm)
> +		return -ENOENT;

[Severity: Critical]
If kvm_file_ref points to a file that was freed and reallocated to a
completely different type of file (due to SLAB_TYPESAFE_BY_RCU), could
this cause type confusion?

Since struct file memory can be reused, extracting private_data without first
verifying the file's operations (f_op) could lead to arbitrary memory
corruption. Should this code use file_is_kvm() or file_to_kvm() before
dereferencing private_data?

> diff --git a/drivers/vfio/pci/vfio_pci_zdev.c b/drivers/vfio/pci/vfio_pci_zdev.c
> index 0990fdb146b78..d3a1101013531 100644
> --- a/drivers/vfio/pci/vfio_pci_zdev.c
> +++ b/drivers/vfio/pci/vfio_pci_zdev.c
[ ... ]
> @@ -144,6 +144,7 @@ int vfio_pci_info_zdev_add_caps(struct vfio_pci_core_device *vdev,
>  int vfio_pci_zdev_open_device(struct vfio_pci_core_device *vdev)
>  {
>  	struct zpci_dev *zdev = to_zpci(vdev->pdev);
> +	struct kvm *kvm;
>  
>  	if (!zdev)
>  		return -ENODEV;
> @@ -151,8 +152,12 @@ int vfio_pci_zdev_open_device(struct vfio_pci_core_device *vdev)
>  	if (!vdev->vdev.kvm)
>  		return 0;
>  
> +	kvm = vdev->vdev.kvm->private_data;
> +	if (!kvm)
> +		return -ENOENT;

[Severity: Critical]
Does this code also need to validate that vdev->vdev.kvm is actually a KVM
file before interpreting its private_data as a struct kvm pointer?

> diff --git a/drivers/vfio/vfio_main.c b/drivers/vfio/vfio_main.c
> index 423ead48aafe3..b06d1a9116051 100644
> --- a/drivers/vfio/vfio_main.c
> +++ b/drivers/vfio/vfio_main.c
[ ... ]
> @@ -472,36 +472,17 @@ void vfio_unregister_group_dev(struct vfio_device *device)
>  EXPORT_SYMBOL_GPL(vfio_unregister_group_dev);
>  
>  #if IS_ENABLED(CONFIG_KVM)
> -void vfio_device_get_kvm_safe(struct vfio_device *device, struct kvm *kvm)
> +void vfio_device_get_kvm_safe(struct vfio_device *device, struct file **kvm)
>  {
> -	void (*pfn)(struct kvm *kvm);
> -	bool (*fn)(struct kvm *kvm);
> -	bool ret;
> +	struct file *kvm_file_ref __free(fput) = NULL;
>  
>  	lockdep_assert_held(&device->dev_set->lock);
>  
> -	if (!kvm)
> +	kvm_file_ref = get_file_active(kvm);
> +	if (!kvm_file_ref)
>  		return;

[Severity: Critical]
Can this result in getting a reference to a completely unrelated file object?

If userspace opens a KVM VM and creates a KVM VFIO device (taking a reference
to the kvm object), VFIO stores a weak pointer to the KVM struct file.

If userspace then closes the KVM VM fd while keeping the KVM VFIO device fd
open:

1. The VM fd closes, dropping the f_count to 0 and freeing the struct file
   via RCU.
2. The kvm->users_count remains > 0 (due to the open KVM VFIO device fd), so
   kvm_destroy_vm() is never called to clear the VFIO weak pointer.
3. Because struct file uses SLAB_TYPESAFE_BY_RCU, the freed memory can be
   reallocated to a completely unrelated file.

When get_file_active() is later called here on the dangling pointer, wouldn't
it successfully take a reference on the reused struct file?

> diff --git a/virt/kvm/vfio.c b/virt/kvm/vfio.c
> index 6cdc4e9a333a3..0166cc4d39b31 100644
> --- a/virt/kvm/vfio.c
> +++ b/virt/kvm/vfio.c
[ ... ]
> @@ -168,7 +168,7 @@ static int kvm_vfio_file_add(struct kvm_device *dev, unsigned int fd)
>  	kvf->file = get_file(filp);
>  	list_add_tail(&kvf->node, &kv->file_list);
>  
> -	kvm_vfio_file_set_kvm(kvf->file, dev->kvm);
> +	kvm_vfio_file_set_kvm(kvf->file, dev->kvm->file);

[Severity: Medium]
Is it safe to access dev->kvm->file directly here?

Since kvm->file is explicitly annotated as a __rcu pointer in struct kvm,
shouldn't this be accessed within an RCU read-side critical section using
rcu_dereference() to avoid data races with kvm_vm_release()?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260812153631.3376090-1-seiden@linux.ibm.com?part=1

  reply	other threads:[~2026-08-12 16:00 UTC|newest]

Thread overview: 74+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-08-12 15:35 [PATCH v6 00/33] KVM: s390: Introduce arm64 KVM Steffen Eiden
2026-08-12 15:35 ` [PATCH v6 01/33] vfio: Use file-based reference counting for KVM Steffen Eiden
2026-08-12 16:00   ` sashiko-bot [this message]
2026-08-12 15:35 ` [PATCH v6 02/33] KVM: Make device name configurable Steffen Eiden
2026-08-12 16:08   ` sashiko-bot
2026-08-12 15:35 ` [PATCH v6 03/33] KVM: Allow KVM implementations to switch off MMIO independent of Kconfig Steffen Eiden
2026-08-12 15:49   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 04/33] arm64: Use proper include variant Steffen Eiden
2026-08-12 15:52   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 05/33] arm64: ptrace: Use constants for compat register numbers Steffen Eiden
2026-08-12 15:46   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 06/33] arm64: sysreg: Convert SPSR_ELx to automatic register generation Steffen Eiden
2026-08-12 15:48   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 07/33] KVM: arm64: Access elements of vcpu_gp_regs individually Steffen Eiden
2026-08-12 15:48   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 08/33] KVM: arm64: Use accessor functions for core regs Steffen Eiden
2026-08-12 15:50   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 09/33] arm64: Prepare sharing arm64 headers with s390 Steffen Eiden
2026-08-12 15:52   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 10/33] arm64: Share " Steffen Eiden
2026-08-12 16:20   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 11/33] KVM: arm64: Share arm64 code " Steffen Eiden
2026-08-12 15:59   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 12/33] KVM: s390: Extract gmap tracing to a separate header Steffen Eiden
2026-08-12 15:57   ` sashiko-bot
2026-08-12 17:13   ` Christian Borntraeger
2026-08-12 15:36 ` [PATCH v6 13/33] KVM: s390: Prepare include guards for a new location Steffen Eiden
2026-08-12 15:53   ` sashiko-bot
2026-08-12 17:35   ` Christian Borntraeger
2026-08-12 15:36 ` [PATCH v6 14/33] KVM: s390: Rename kvm-s390.{c,h} to s390.{c,h} Steffen Eiden
2026-08-12 15:58   ` sashiko-bot
2026-08-12 17:58   ` Christian Borntraeger
2026-08-12 15:36 ` [PATCH v6 15/33] KVM: s390: Move kvm_host definitions to kvm_host_s390 Steffen Eiden
2026-08-12 15:54   ` sashiko-bot
2026-08-12 18:12   ` Christian Borntraeger
2026-08-12 15:36 ` [PATCH v6 16/33] KVM: s390: Move s390 kvm code into a subdirectory Steffen Eiden
2026-08-12 16:02   ` sashiko-bot
2026-08-12 18:32   ` Christian Borntraeger
2026-08-12 15:36 ` [PATCH v6 17/33] KVM: s390: Move PGM code definitions to asm/kvm_host.h Steffen Eiden
2026-08-12 16:04   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 18/33] KVM: s390: Prepare gmap for a second KVM implementation Steffen Eiden
2026-08-12 16:10   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 19/33] KVM: s390: gmap: Make storage keys optional Steffen Eiden
2026-08-12 16:06   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 20/33] KVM: s390: gmap: Make CMMA optional Steffen Eiden
2026-08-12 16:09   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 21/33] KVM: s390: gmap: Make prefix handling optional Steffen Eiden
2026-08-12 16:08   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 22/33] KVM: s390: Prepare KVM/s390 for a second KVM module Steffen Eiden
2026-08-12 16:21   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 23/33] s390: Use arm64 headers Steffen Eiden
2026-08-12 16:23   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 24/33] KVM: s390: Use arm64 code Steffen Eiden
2026-08-12 16:18   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 25/33] s390: Introduce Start Arm Execution instruction Steffen Eiden
2026-08-12 16:24   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 26/33] KVM: s390: arm64: Introduce host definitions Steffen Eiden
2026-08-12 16:27   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 27/33] s390/hwcaps: Report SAE support as hwcap Steffen Eiden
2026-08-12 16:15   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 28/33] KVM: s390: Add basic arm64 kvm module Steffen Eiden
2026-08-12 16:23   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 29/33] KVM: s390: arm64: Implement required functions Steffen Eiden
2026-08-12 16:36   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 30/33] KVM: s390: arm64: Implement vm/vcpu create destroy Steffen Eiden
2026-08-12 16:38   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 31/33] KVM: s390: arm64: Implement vCPU IOCTLs Steffen Eiden
2026-08-12 16:41   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 32/33] KVM: s390: arm64: Implement basic page fault handler Steffen Eiden
2026-08-12 16:34   ` sashiko-bot
2026-08-12 15:36 ` [PATCH v6 33/33] KVM: s390: arm64: Enable KVM_ARM64 config and Kbuild Steffen Eiden
2026-08-12 16:59   ` sashiko-bot
2026-08-12 16:28 ` [PATCH v6 00/33] KVM: s390: Introduce arm64 KVM Christian Borntraeger
2026-08-12 16:36   ` Sean Christopherson

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260812160049.4D4321F000E9@smtp.kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=agordeev@linux.ibm.com \
    --cc=borntraeger@linux.ibm.vom \
    --cc=gor@linux.ibm.com \
    --cc=hca@linux.ibm.com \
    --cc=kvm@vger.kernel.org \
    --cc=kvmarm@lists.linux.dev \
    --cc=linux-s390@vger.kernel.org \
    --cc=maz@kernel.org \
    --cc=oupton@kernel.org \
    --cc=sashiko-reviews@lists.linux.dev \
    --cc=seiden@linux.ibm.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox