most: usb: fix double free on late probe failure
Subsystems (2)
PATCH 1/1 most: usb: fix double free on late probe failure
The MOST subsystem has a non-standard registration function which frees the interface on registration failures and on deregistration.
This unsurprisingly leads to bugs in the MOST drivers, and a couple of recent changes turned a reference underflow and use-after-free in the USB driver into several double free and a use-after-free on late probe failures.
Fixes 723de0f9171e ("staging: most: remove device from interface structure")
Fixes 4b1270902609 ("most: usb: Fix use-after-free in hdm_disconnect")
Fixes a8cc9e5fcb0e ("most: usb: hdm_probe: Fix calling put_device() before device initialization")
Cc Christian Gromm <[email protected]>
Cc Victoria Votokina <[email protected]>
Signed-off-by Johan Hovold <[email protected]>
--- drivers/most/most_usb.c | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-)
drivers/most/most_usb.c +5 -9
@@ -1058,7 +1058,7 @@ hdm_probe(struct usb_interface *interface, const struct usb_device_id *id) ret =most_register_interface (&mdev->iface);if (ret) - goto err_free_busy_urbs; +return ret;mutex_lock (&mdev->io_mutex); if (le16_to_cpu(usb_dev->descriptor.idProduct) == USB_DEV_ID_OS81118 ||
@@ -1068,8 +1068,7 @@ hdm_probe(struct usb_interface *interface, const struct usb_device_id *id)if (!mdev->dci) {mutex_unlock (&mdev->io_mutex);most_deregister_interface (&mdev->iface); - ret = -ENOMEM ; - goto err_free_busy_urbs; +return -ENOMEM ; } mdev->dci->dev.init_name ="dci" ;
@@ -1078,18 +1077,15 @@ hdm_probe(struct usb_interface *interface, const struct usb_device_id *id) mdev->dci->dev.release = release_dci;if (device_register (&mdev->dci->dev)) {mutex_unlock (&mdev->io_mutex); +put_device (&mdev->dci->dev);most_deregister_interface (&mdev->iface); - ret = -ENOMEM ; - goto err_free_dci; +return -ENOMEM ; } mdev->dci->usb_device = mdev->usb_device; }mutex_unlock (&mdev->io_mutex);return 0 ; -err_free_dci: -put_device (&mdev->dci->dev); -err_free_busy_urbs: -kfree (mdev->busy_urbs); + err_free_ep_address:kfree (mdev->ep_address); err_free_cap:
Signature · 1 line
2.51.0