speedtch testatm.c,1.4,1.5

Roman Kagan rkagan at mail.ru
Fri Apr 8 06:19:22 EDT 2005


On Fri, Apr 08, 2005 at 02:12:27PM +0400, Roman Kagan wrote:
> On Thu, Apr 07, 2005 at 11:16:20PM +0100, Duncan Sands wrote:
> > Modified Files:
> > 	testatm.c 
> > Log Message:
> > Add a driver that claims all interfaces (and drops them all whenever any
> > one of them is disconnected).  It seems to have exposed a USB bug: if you
> > plug in a device with more than one interface and use driver 8 on it, then
> > force a logical (rather than a physical) disconnect, then afterwards the
> > module cannot be unloaded and rmmod spins taking up all CPU.  For example,
> > just try to remove the testatm module without unplugging the device.
> 
> Can't it be because you release all interfaces including the one
> disconnect is called with?

How about this?

Roman.

Index: testatm.c
===================================================================
RCS file: /home/cvs/usbatm/testatm.c,v
retrieving revision 1.5
diff -u -p -r1.5 testatm.c
--- testatm.c	7 Apr 2005 22:16:18 -0000	1.5
+++ testatm.c	8 Apr 2005 10:18:41 -0000
@@ -216,12 +216,12 @@ static struct usb_driver testatm_usb_dri
 	.id_table	= testatm_usb_ids
 };
 
-static void release_interfaces(struct usb_device *usb_dev, int num_interfaces) {
+static void release_interfaces(struct usb_device *usb_dev, int num_interfaces, int exclude_if) {
 	struct usb_interface *cur_intf;
 	int i;
 
 	for(i = 0; i < num_interfaces; i++)
-		if ((cur_intf = usb_ifnum_to_if(usb_dev, i))) {
+		if ((cur_intf = usb_ifnum_to_if(usb_dev, i)) && i != exclude_if) {
 			usb_set_intfdata(cur_intf, NULL);
 			usb_driver_release_interface(&testatm_usb_driver, cur_intf);
 		}
@@ -245,7 +245,7 @@ static int claim_bind(struct usbatm_data
 
 			if (ret < 0) {
 				usb_dbg(usbatm, "%s: failed to claim interface %d (%d)\n", __func__, i, ret);
-				release_interfaces(usb_dev, i);
+				release_interfaces(usb_dev, i, ifnum);
 				return ret;
 			}
 		}
@@ -258,10 +258,11 @@ void claim_unbind(struct usbatm_data *us
 {
 	struct usb_device *usb_dev = interface_to_usbdev(intf);
 	int num_interfaces = usb_dev->actconfig->desc.bNumInterfaces;
+	int ifnum = intf->altsetting->desc.bInterfaceNumber;
 
 	dbg("claim_unbind");
 
-	release_interfaces(usb_dev, num_interfaces);
+	release_interfaces(usb_dev, num_interfaces, ifnum);
 }
 
 static int __init testatm_init(void)



More information about the Usbatm mailing list