Skip to content

[s390] s390/pci: cleanup resources only if necessary

Claudio Imbrenda requested to merge cimbrend/centos-stream-9:bz2034132 into main

Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=2034132 Upstream Status: git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git Build info: https://brewweb.engineering.redhat.com/brew/taskinfo?taskID=42324992 Tested: by IBM Conflicts: None

Description: s390/pci: Use-after-free of zpci_dev objects Symptom: When using Reassign I/O Path with multi-function PCI devices and removing the function for port 1 before that of port 2 a NULL pointer reference can be triggered crashing the kernel. Problem: The removal of the function with devfn zero before other functions of the same device may lead to the PCI core keeping a reference to the pci_dev even after the underlying zpci_dev was reserved. This was not antipated in the original multi-function support and was not originally discovered during testing because the PCI core does not keep the pci_dev reference alive on all kernel versions and under all circumstances. The zpci_dev reference counting still only accounts for a single reference held by the zPCI subsytem which does not match up with the PCI common core's use of reference counting for pci_dev which, through it's sysdata zbus pointer references its underlying zpci_dev. Solution: We need to account for the long lived reference to the struct zpci_dev held by the pci_dev and also make sure we only try to reserve a zpci_dev once even if multiple events indicate the reservation of the device. Reproduction: This can be reproduced, though not 100% reliably especially on older kernels, by doing a "Reassign I/O Path" operation for each PF of a ConnectX-5 card with the PF for port 1 before that for port 2. On some kernels the removal of the second PF leads to an immediate crash. If that is not observed inspection of /sys/kernel/debug/s390dbf/pci_msg/sprintf still shows that the function for the first PF is fully freed even though the second PF still holds a reference via pci_dev->sriov->dev.

Signed-off-by: Claudio Imbrenda cimbrend@redhat.com

Edited by Claudio Imbrenda

Merge request reports