From: "Signed-off-by: Lan Tianyu" <tianyu.lan@xxxxxxxxx> ACPI provide "_PLD" and "_UPC" aml methods to describe usb port visibility and connectability. This patch is to use those information to set usb port's DeviceRemovable. Signed-off-by: Lan Tianyu <tianyu.lan@xxxxxxxxx> --- drivers/usb/core/hub.c | 7 +++++++ drivers/usb/core/usb.h | 4 ---- drivers/usb/host/ehci-hub.c | 10 +++++++++- include/linux/usb.h | 4 ++++ 4 files changed, 20 insertions(+), 5 deletions(-) diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index 65c91300..4c631d3 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -1560,6 +1560,10 @@ static int hub_configure(struct usb_hub *hub, dev_err(hub->intfdev, "couldn't create port%d device.\n", i + 1); + /* Get hub descripor again to sync port's DeviceRemovable + * after the usb port devices being created. + */ + get_hub_descriptor(hdev, hub->descriptor); hub_activate(hub, HUB_INIT); return 0; @@ -5254,6 +5258,9 @@ usb_get_hub_port_connect_type(struct usb_device *hdev, int port1) { struct usb_hub *hub = hdev_to_hub(hdev); + if (!hub) + return USB_PORT_CONNECT_TYPE_UNKNOWN; + return hub->ports[port1 - 1]->connect_type; } diff --git a/drivers/usb/core/usb.h b/drivers/usb/core/usb.h index 9bfe1ba..e687de2 100644 --- a/drivers/usb/core/usb.h +++ b/drivers/usb/core/usb.h @@ -172,10 +172,6 @@ extern void usb_notify_add_device(struct usb_device *udev); 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); #ifdef CONFIG_ACPI extern int usb_acpi_register(void); diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c index c788022..0a3bb05 100644 --- a/drivers/usb/host/ehci-hub.c +++ b/drivers/usb/host/ehci-hub.c @@ -636,6 +636,7 @@ ehci_hub_descriptor ( struct usb_hub_descriptor *desc ) { int ports = HCS_N_PORTS (ehci->hcs_params); + int i; u16 temp; desc->bDescriptorType = 0x29; @@ -648,7 +649,14 @@ ehci_hub_descriptor ( /* two bitmaps: ports removable, and usb 1.0 legacy PortPwrCtrlMask */ memset(&desc->u.hs.DeviceRemovable[0], 0, temp); - memset(&desc->u.hs.DeviceRemovable[temp], 0xff, temp); + memset(&desc->u.hs.DeviceRemovable[temp], 0xff, ltemp); + + for (i = 1; i <= ports; i++) { + if (usb_get_hub_port_connect_type(hcd->self.root_hub, i); + == USB_PORT_CONNECT_TYPE_HARD_WIRED) + desc->u.hs.DeviceRemovable[ports/8] |= 1 << (i%8); + } + temp = 0x0008; /* per-port overcurrent reporting */ if (HCS_PPC (ehci->hcs_params)) diff --git a/include/linux/usb.h b/include/linux/usb.h index 07915a3..0928f2a 100644 --- a/include/linux/usb.h +++ b/include/linux/usb.h @@ -575,6 +575,10 @@ static inline struct usb_device *interface_to_usbdev(struct usb_interface *intf) return to_usb_device(intf->dev.parent); } +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 struct usb_device *usb_get_dev(struct usb_device *dev); extern void usb_put_dev(struct usb_device *dev); extern struct usb_device *usb_hub_find_child(struct usb_device *hdev, -- 1.7.9.5 -- 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