On 2012年11月29日 08:08, Alan Stern wrote: > On Wed, 28 Nov 2012, Sarah Sharp wrote: > >>>> The shared code to overwrite the bits should probably print a warning if >>>> the host and ACPI bits differ. >>> >>> I'm not so sure about that. For one thing, who wants warnings to be >>> logged every time they run "lsusb -v"? >> >> Yeah, that's probably not a great idea. >> >>> Also, this sort of thing might be more common than you might expect. >>> I'd guess that if the ACPI information contains anything useful at all, >>> it will be different from the [Ex]HCI information. >>> >>> Tianyu's patches log such warnings for xHCI but not for EHCI. That >>> inconsistency is another reason to rework them. >> >> Tianyu did that because I asked him to for xHCI. I didn't think about >> the lsusb implications. You're right that it will probably be annoying >> to the user, so he should just drop the warning in the shared code. > > It could be changed to a dev_dbg. That wouldn't bother people and it > might be useful. > > Alan Stern > Hi Alan: how about following patch? Index: usb/drivers/usb/core/hub.c =================================================================== --- usb.orig/drivers/usb/core/hub.c +++ usb/drivers/usb/core/hub.c @@ -1441,6 +1441,8 @@ static int hub_configure(struct usb_hub dev_err(hub->intfdev, "couldn't create port%d device.\n", i + 1); + usb_hub_adjust_DeviceRemovable(hdev, hub->descriptor); + hub_activate(hub, HUB_INIT); return 0; @@ -5086,8 +5088,56 @@ usb_get_hub_port_connect_type(struct usb { struct usb_hub *hub = hdev_to_hub(hdev); + if (!hub) + return USB_PORT_CONNECT_TYPE_UNKNOWN; + return hub->ports[port1 - 1]->connect_type; } +EXPORT_SYMBOL_GPL(usb_get_hub_port_connect_type); + +void usb_hub_adjust_DeviceRemovable(struct usb_device *hdev, + struct usb_hub_descriptor *desc) +{ + enum usb_port_connect_type connect_type; + int i; + + if (!hub_is_superspeed(hdev)) { + for (i = 1; i <= hdev->maxchild; i++) { + connect_type = + usb_get_hub_port_connect_type(hdev, i); + + if (connect_type == USB_PORT_CONNECT_TYPE_HARD_WIRED) { + u8 mask = 1 << (i%8); + + if (!(desc->u.hs.DeviceRemovable[i/8] & mask)) + dev_dbg(&hdev->dev, "usb2.0 port%d's DeviceRemovable is changed to 1 according platform information.\n", i); + + desc->u.hs.DeviceRemovable[i/8] + |= mask; + } + } + } else { + u16 port_removable = + le16_to_cpu(desc->u.ss.DeviceRemovable); + + for (i = 1; i <= hdev->maxchild; i++) { + connect_type = + usb_get_hub_port_connect_type(hdev, i); + + if (connect_type == USB_PORT_CONNECT_TYPE_HARD_WIRED) { + u16 mask = 1 << i; + + if (!(port_removable & mask)) + dev_dbg(&hdev->dev, "usb3.0 port%d's DeviceRemovable is changed to 1 according platform information.\n", i); + + port_removable |= mask; + } + } + + desc->u.ss.DeviceRemovable = + cpu_to_le16(port_removable); + } +} #ifdef CONFIG_ACPI /** Index: usb/drivers/usb/core/usb.h =================================================================== --- usb.orig/drivers/usb/core/usb.h +++ usb/drivers/usb/core/usb.h @@ -1,5 +1,6 @@ #include <linux/pm.h> #include <linux/acpi.h> +#include <linux/usb/ch11.h> struct dev_state; @@ -169,10 +170,13 @@ extern void usb_notify_add_device(struct extern void usb_notify_remove_device(struct usb_device *udev); extern void usb_notify_add_bus(struct usb_bus *ubus); extern void usb_notify_remove_bus(struct usb_bus *ubus); + extern enum usb_port_connect_type usb_get_hub_port_connect_type(struct usb_device *hdev, int port1); extern void usb_set_hub_port_connect_type(struct usb_device *hdev, int port1, enum usb_port_connect_type type); +extern void usb_hub_adjust_DeviceRemovable(struct usb_device *hdev, + struct usb_hub_descriptor *desc); #ifdef CONFIG_ACPI extern int usb_acpi_register(void); Index: usb/drivers/usb/core/hcd.c =================================================================== --- usb.orig/drivers/usb/core/hcd.c +++ usb/drivers/usb/core/hcd.c @@ -619,6 +619,10 @@ nongeneric: status = hcd->driver->hub_control (hcd, typeReq, wValue, wIndex, tbuf, wLength); + + if (typeReq == GetHubDescriptor) + usb_hub_adjust_DeviceRemovable(hcd->self.root_hub, + (struct usb_hub_descriptor*)tbuf); break; error: /* "protocol stall" on error */ -- Best regards Tianyu Lan -- To unsubscribe from this list: send the line "unsubscribe linux-usb" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html