git: 96e86aa6faa6 - main - LinuxKPI: pci: deal with kobject_add() being able to fail
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Fri, 09 May 2025 19:45:59 UTC
The branch main has been updated by bz:
URL: https://cgit.FreeBSD.org/src/commit/?id=96e86aa6faa6fde4ff75fd757db55afe9e4be132
commit 96e86aa6faa6fde4ff75fd757db55afe9e4be132
Author: Bjoern A. Zeeb <bz@FreeBSD.org>
AuthorDate: 2025-05-04 19:58:15 +0000
Commit: Bjoern A. Zeeb <bz@FreeBSD.org>
CommitDate: 2025-05-09 19:45:09 +0000
LinuxKPI: pci: deal with kobject_add() being able to fail
lkpifill_pci_dev() uses a sequene of kobject_init/set_name/add.
The problem is that kobject_add could fail.
Move the entire logic to the beginning of the function,
switch to kobject_init_and_add() and check the return code.
Make lkpifill_pci_dev() return the error and deal in the callers
with a possible error accordingly.
Sponsored by: The FreeBSD Foundation
MFC after: 3 days
Reviewed by: dumbbell
Differential Revision: https://reviews.freebsd.org/D50154
---
sys/compat/linuxkpi/common/src/linux_pci.c | 29 ++++++++++++++++++++++-------
1 file changed, 22 insertions(+), 7 deletions(-)
diff --git a/sys/compat/linuxkpi/common/src/linux_pci.c b/sys/compat/linuxkpi/common/src/linux_pci.c
index fa5e3c71fad0..3651946c6ee5 100644
--- a/sys/compat/linuxkpi/common/src/linux_pci.c
+++ b/sys/compat/linuxkpi/common/src/linux_pci.c
@@ -309,9 +309,18 @@ lkpi_pci_dev_release(struct device *dev)
spin_lock_destroy(&dev->devres_lock);
}
-static void
+static int
lkpifill_pci_dev(device_t dev, struct pci_dev *pdev)
{
+ int error;
+
+ error = kobject_init_and_add(&pdev->dev.kobj, &linux_dev_ktype,
+ &linux_root_device.kobj, device_get_nameunit(dev));
+ if (error != 0) {
+ printf("%s:%d: kobject_init_and_add returned %d\n",
+ __func__, __LINE__, error);
+ return (error);
+ }
pdev->devfn = PCI_DEVFN(pci_get_slot(dev), pci_get_function(dev));
pdev->vendor = pci_get_vendor(dev);
@@ -341,12 +350,10 @@ lkpifill_pci_dev(device_t dev, struct pci_dev *pdev)
pdev->msi_desc = malloc(pci_msi_count(dev) *
sizeof(*pdev->msi_desc), M_DEVBUF, M_WAITOK | M_ZERO);
- kobject_init(&pdev->dev.kobj, &linux_dev_ktype);
- kobject_set_name(&pdev->dev.kobj, device_get_nameunit(dev));
- kobject_add(&pdev->dev.kobj, &linux_root_device.kobj,
- kobject_name(&pdev->dev.kobj));
spin_lock_init(&pdev->dev.devres_lock);
INIT_LIST_HEAD(&pdev->dev.devres_head);
+
+ return (0);
}
static void
@@ -374,9 +381,14 @@ struct pci_dev *
lkpinew_pci_dev(device_t dev)
{
struct pci_dev *pdev;
+ int error;
pdev = malloc(sizeof(*pdev), M_DEVBUF, M_WAITOK|M_ZERO);
- lkpifill_pci_dev(dev, pdev);
+ error = lkpifill_pci_dev(dev, pdev);
+ if (error != 0) {
+ free(pdev, M_DEVBUF);
+ return (NULL);
+ }
pdev->dev.release = lkpinew_pci_dev_release;
return (pdev);
@@ -525,7 +537,10 @@ linux_pci_attach_device(device_t dev, struct pci_driver *pdrv,
device_set_ivars(dev, dinfo);
}
- lkpifill_pci_dev(dev, pdev);
+ error = lkpifill_pci_dev(dev, pdev);
+ if (error != 0)
+ return (error);
+
if (isdrm)
PCI_GET_ID(device_get_parent(parent), parent, PCI_ID_RID, &rid);
else